aboutsummaryrefslogtreecommitdiff
path: root/src/client/views/collections
diff options
context:
space:
mode:
authorSam Wilkins <abdullah_ahmed@brown.edu>2019-07-23 19:12:15 -0400
committerSam Wilkins <abdullah_ahmed@brown.edu>2019-07-23 19:12:15 -0400
commit0ef6d9b5a3f90552562f4a6392967887d8805cc3 (patch)
treea40f95ecf9ae19d836a7bd324ed650d78fc7c3c0 /src/client/views/collections
parent7d9958f23b2b69f59bb108b33ec014b52ad41c99 (diff)
parent86971952237b8bd01a23b52db662740126bd8477 (diff)
merge
Diffstat (limited to 'src/client/views/collections')
-rw-r--r--src/client/views/collections/CollectionBaseView.tsx6
-rw-r--r--src/client/views/collections/CollectionDockingView.tsx2
-rw-r--r--src/client/views/collections/CollectionSchemaView.tsx12
-rw-r--r--src/client/views/collections/CollectionStackingView.scss13
-rw-r--r--src/client/views/collections/CollectionStackingView.tsx102
-rw-r--r--src/client/views/collections/CollectionSubView.tsx11
-rw-r--r--src/client/views/collections/CollectionTreeView.tsx79
-rw-r--r--src/client/views/collections/CollectionVideoView.tsx40
-rw-r--r--src/client/views/collections/CollectionView.tsx27
-rw-r--r--src/client/views/collections/collectionFreeForm/CollectionFreeFormView.tsx19
10 files changed, 193 insertions, 118 deletions
diff --git a/src/client/views/collections/CollectionBaseView.tsx b/src/client/views/collections/CollectionBaseView.tsx
index eba69b448..72faf52c4 100644
--- a/src/client/views/collections/CollectionBaseView.tsx
+++ b/src/client/views/collections/CollectionBaseView.tsx
@@ -18,7 +18,8 @@ export enum CollectionViewType {
Schema,
Docking,
Tree,
- Stacking
+ Stacking,
+ Masonry
}
export interface CollectionRenderProps {
@@ -78,7 +79,6 @@ export class CollectionBaseView extends React.Component<CollectionViewProps> {
@action.bound
addDocument(doc: Doc, allowDuplicates: boolean = false): boolean {
- let self = this;
var curPage = NumCast(this.props.Document.curPage, -1);
Doc.GetProto(doc).page = curPage;
if (curPage >= 0) {
@@ -146,7 +146,7 @@ export class CollectionBaseView extends React.Component<CollectionViewProps> {
const viewtype = this.collectionViewType;
return (
<div id="collectionBaseView"
- style={{ boxShadow: `#9c9396 ${StrCast(this.props.Document.boxShadow, "0.2vw 0.2vw 0.8vw")}` }}
+ style={{ overflow: "auto", boxShadow: `#9c9396 ${StrCast(this.props.Document.boxShadow, "0.2vw 0.2vw 0.8vw")}` }}
className={this.props.className || "collectionView-cont"}
onContextMenu={this.props.onContextMenu} ref={this.props.contentRef}>
{viewtype !== undefined ? this.props.children(viewtype, props) : (null)}
diff --git a/src/client/views/collections/CollectionDockingView.tsx b/src/client/views/collections/CollectionDockingView.tsx
index a193ff677..ba7903419 100644
--- a/src/client/views/collections/CollectionDockingView.tsx
+++ b/src/client/views/collections/CollectionDockingView.tsx
@@ -465,7 +465,7 @@ export class CollectionDockingView extends React.Component<SubCollectionViewProp
.off('click') //unbind the current click handler
.click(action(function () {
stack.config.fixed = !stack.config.fixed;
- // var url = DocServer.prepend("/doc/" + stack.contentItems[0].tab.contentItem.config.props.documentId);
+ // var url = Utils.prepend("/doc/" + stack.contentItems[0].tab.contentItem.config.props.documentId);
// let win = window.open(url, stack.contentItems[0].tab.title, "width=300,height=400");
}));
}
diff --git a/src/client/views/collections/CollectionSchemaView.tsx b/src/client/views/collections/CollectionSchemaView.tsx
index 6d71823c2..39844dea2 100644
--- a/src/client/views/collections/CollectionSchemaView.tsx
+++ b/src/client/views/collections/CollectionSchemaView.tsx
@@ -31,11 +31,17 @@ import { CollectionVideoView } from "./CollectionVideoView";
import { CollectionView } from "./CollectionView";
import { undoBatch } from "../../util/UndoManager";
import { timesSeries } from "async";
+<<<<<<< HEAD
import { CollectionSchemaHeader, CollectionSchemaAddColumnHeader } from "./CollectionSchemaHeaders";
import { CellProps, CollectionSchemaCell, CollectionSchemaNumberCell, CollectionSchemaStringCell, CollectionSchemaBooleanCell, CollectionSchemaCheckboxCell, CollectionSchemaDocCell } from "./CollectionSchemaCells";
import { MovableColumn, MovableRow } from "./CollectionSchemaMovableTableHOC";
import { SelectionManager } from "../../util/SelectionManager";
import { DocumentManager } from "../../util/DocumentManager";
+=======
+import { ImageBox } from "../nodes/ImageBox";
+import { ComputedField } from "../../../new_fields/ScriptField";
+
+>>>>>>> 86971952237b8bd01a23b52db662740126bd8477
library.add(faCog);
library.add(faPlus);
@@ -729,8 +735,12 @@ export class CollectionSchemaPreview extends React.Component<CollectionSchemaPre
drop = (e: Event, de: DragManager.DropEvent) => {
if (de.data instanceof DragManager.DocumentDragData) {
let docDrag = de.data;
+ let computed = CompileScript("return this.image_data[0]", { params: { this: "Doc" } });
this.props.childDocs && this.props.childDocs.map(otherdoc => {
- Doc.GetProto(otherdoc).layout = Doc.MakeDelegate(docDrag.draggedDocuments[0]);
+ let doc = docDrag.draggedDocuments[0];
+ let target = Doc.GetProto(otherdoc);
+ target.layout = target.detailedLayout = Doc.MakeDelegate(doc);
+ computed.compiled && (target.miniLayout = new ComputedField(computed));
});
e.stopPropagation();
}
diff --git a/src/client/views/collections/CollectionStackingView.scss b/src/client/views/collections/CollectionStackingView.scss
index 7e886304d..7ebf5f77c 100644
--- a/src/client/views/collections/CollectionStackingView.scss
+++ b/src/client/views/collections/CollectionStackingView.scss
@@ -1,7 +1,9 @@
@import "../globalCssVariables";
.collectionStackingView {
+ height: 100%;
+ width: 100%;
+ position: absolute;
overflow-y: auto;
-
.collectionStackingView-docView-container {
width: 45%;
margin: 5% 2.5%;
@@ -71,4 +73,13 @@
grid-column-end: span 1;
height: 100%;
}
+ .collectionStackingView-sectionHeader {
+ width: 90%;
+ background: gray;
+ text-align: center;
+ margin-left: 5%;
+ margin-right: 5%;
+ color: white;
+ margin-top: 10px;
+ }
} \ No newline at end of file
diff --git a/src/client/views/collections/CollectionStackingView.tsx b/src/client/views/collections/CollectionStackingView.tsx
index fe01103d6..54b0e37b5 100644
--- a/src/client/views/collections/CollectionStackingView.tsx
+++ b/src/client/views/collections/CollectionStackingView.tsx
@@ -1,12 +1,11 @@
import React = require("react");
import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
-import { action, computed, IReactionDisposer, reaction, untracked } from "mobx";
+import { action, computed, IReactionDisposer, reaction, untracked, observable, runInAction } from "mobx";
import { observer } from "mobx-react";
import { Doc, HeightSym, WidthSym } from "../../../new_fields/Doc";
import { Id } from "../../../new_fields/FieldSymbols";
-import { BoolCast, NumCast, Cast } from "../../../new_fields/Types";
-import { emptyFunction, Utils } from "../../../Utils";
-import { ContextMenu } from "../ContextMenu";
+import { BoolCast, NumCast, Cast, StrCast } from "../../../new_fields/Types";
+import { emptyFunction, Utils, returnTrue } from "../../../Utils";
import { CollectionSchemaPreview } from "./CollectionSchemaView";
import "./CollectionStackingView.scss";
import { CollectionSubView } from "./CollectionSubView";
@@ -14,14 +13,16 @@ import { undoBatch } from "../../util/UndoManager";
import { DragManager } from "../../util/DragManager";
import { DocumentType } from "../../documents/Documents";
import { Transform } from "../../util/Transform";
+import { CursorProperty } from "csstype";
@observer
export class CollectionStackingView extends CollectionSubView(doc => doc) {
_masonryGridRef: HTMLDivElement | null = null;
_draggerRef = React.createRef<HTMLDivElement>();
_heightDisposer?: IReactionDisposer;
- _gridSize = 1;
_docXfs: any[] = [];
+ _columnStart: number = 0;
+ @observable private cursor: CursorProperty = "grab";
@computed get xMargin() { return NumCast(this.props.Document.xMargin, 2 * this.gridGap); }
@computed get yMargin() { return NumCast(this.props.Document.yMargin, 2 * this.gridGap); }
@computed get gridGap() { return NumCast(this.props.Document.gridGap, 10); }
@@ -29,15 +30,25 @@ export class CollectionStackingView extends CollectionSubView(doc => doc) {
@computed get columnWidth() { return this.singleColumn ? (this.props.PanelWidth() / (this.props as any).ContentScaling() - 2 * this.xMargin) : Math.min(this.props.PanelWidth() - 2 * this.xMargin, NumCast(this.props.Document.columnWidth, 250)); }
@computed get filteredChildren() { return this.childDocs.filter(d => !d.isMinimized); }
+ @computed get Sections() {
+ let sectionFilter = StrCast(this.props.Document.sectionFilter);
+ let fields = new Map<object, Doc[]>();
+ sectionFilter && this.filteredChildren.map(d => {
+ let sectionValue = (d[sectionFilter] ? d[sectionFilter] : "-undefined-") as object;
+ if (!fields.has(sectionValue)) fields.set(sectionValue, [d]);
+ else fields.get(sectionValue)!.push(d);
+ });
+ return fields;
+ }
componentDidMount() {
this._heightDisposer = reaction(() => [this.yMargin, this.gridGap, this.columnWidth, this.childDocs.map(d => [d.height, d.width, d.zoomBasis, d.nativeHeight, d.nativeWidth, d.isMinimized])],
() => this.singleColumn &&
- (this.props.Document.height = this.filteredChildren.reduce((height, d, i) =>
+ (this.props.Document.height = this.Sections.size * 50 + this.filteredChildren.reduce((height, d, i) =>
height + this.getDocHeight(d) + (i === this.filteredChildren.length - 1 ? this.yMargin : this.gridGap), this.yMargin))
, { fireImmediately: true });
}
componentWillUnmount() {
- if (this._heightDisposer) this._heightDisposer();
+ this._heightDisposer && this._heightDisposer();
}
@action
@@ -63,6 +74,7 @@ export class CollectionStackingView extends CollectionSubView(doc => doc) {
DataDocument={resolvedDataDoc}
showOverlays={this.overlays}
renderDepth={this.props.renderDepth}
+ fitToBox={true}
width={width}
height={height}
getTransform={finalDxf}
@@ -85,7 +97,6 @@ export class CollectionStackingView extends CollectionSubView(doc => doc) {
return (nw && nh) ? wid * aspect : d[HeightSym]();
}
-
offsetTransform(doc: Doc, translateX: number, translateY: number) {
let outerXf = Utils.GetScreenTransform(this._masonryGridRef!);
let offset = this.props.ScreenToLocalTransform().transformDirection(outerXf.translateX - translateX, outerXf.translateY - translateY);
@@ -95,6 +106,7 @@ export class CollectionStackingView extends CollectionSubView(doc => doc) {
let { scale, translateX, translateY } = Utils.GetScreenTransform(dref);
return this.offsetTransform(doc, translateX, translateY);
}
+
getSingleDocTransform(doc: Doc, ind: number, width: number) {
let localY = this.filteredChildren.reduce((height, d, i) =>
height + (i < ind ? this.getDocHeight(Doc.expandTemplateLayout(d, this.props.DataDoc)) + this.gridGap : 0), this.yMargin);
@@ -102,24 +114,24 @@ export class CollectionStackingView extends CollectionSubView(doc => doc) {
return this.offsetTransform(doc, translate[0], translate[1]);
}
- @computed
- get children() {
+ children(docs: Doc[]) {
this._docXfs.length = 0;
- return this.filteredChildren.map((d, i) => {
+ return docs.map((d, i) => {
let layoutDoc = Doc.expandTemplateLayout(d, this.props.DataDoc);
let width = () => d.nativeWidth ? Math.min(layoutDoc[WidthSym](), this.columnWidth) : this.columnWidth;
let height = () => this.getDocHeight(layoutDoc);
if (this.singleColumn) {
+ //have to add the height of all previous single column sections or the doc decorations will be in the wrong place.
let dxf = () => this.getSingleDocTransform(layoutDoc, i, width());
- let rowHgtPcnt = height() / (this.props.Document[HeightSym]() - 2 * this.yMargin) * 100;
+ let rowHgtPcnt = height();
this._docXfs.push({ dxf: dxf, width: width, height: height });
- return <div className="collectionStackingView-columnDoc" key={d[Id]} style={{ width: width(), marginTop: i === 0 ? 0 : this.gridGap, height: `${rowHgtPcnt}%` }} >
+ return <div className="collectionStackingView-columnDoc" key={d[Id]} style={{ width: width(), marginTop: i === 0 ? 0 : this.gridGap, height: `${rowHgtPcnt}` }} >
{this.getDisplayDoc(layoutDoc, d, dxf)}
</div>;
} else {
let dref = React.createRef<HTMLDivElement>();
let dxf = () => this.getDocTransform(layoutDoc, dref.current!);
- let rowSpan = Math.ceil((height() + this.gridGap) / (this._gridSize + this.gridGap));
+ let rowSpan = Math.ceil((height() + this.gridGap) / this.gridGap);
this._docXfs.push({ dxf: dxf, width: width, height: height });
return <div className="collectionStackingView-masonryDoc" key={d[Id]} ref={dref} style={{ gridRowEnd: `span ${rowSpan}` }} >
{this.getDisplayDoc(layoutDoc, d, dxf)}
@@ -128,10 +140,10 @@ export class CollectionStackingView extends CollectionSubView(doc => doc) {
});
}
- _columnStart: number = 0;
columnDividerDown = (e: React.PointerEvent) => {
e.stopPropagation();
e.preventDefault();
+ runInAction(() => this.cursor = "grabbing");
document.addEventListener("pointermove", this.onDividerMove);
document.addEventListener('pointerup', this.onDividerUp);
this._columnStart = this.props.ScreenToLocalTransform().transformPoint(e.clientX, e.clientY)[0];
@@ -141,29 +153,21 @@ export class CollectionStackingView extends CollectionSubView(doc => doc) {
let dragPos = this.props.ScreenToLocalTransform().transformPoint(e.clientX, e.clientY)[0];
let delta = dragPos - this._columnStart;
this._columnStart = dragPos;
-
this.props.Document.columnWidth = this.columnWidth + delta;
}
@action
onDividerUp = (e: PointerEvent): void => {
+ runInAction(() => this.cursor = "grab");
document.removeEventListener("pointermove", this.onDividerMove);
document.removeEventListener('pointerup', this.onDividerUp);
}
@computed get columnDragger() {
- return <div className="collectionStackingView-columnDragger" onPointerDown={this.columnDividerDown} ref={this._draggerRef} style={{ left: `${this.columnWidth + this.xMargin}px` }} >
- <FontAwesomeIcon icon={"caret-down"} />
+ return <div className="collectionStackingView-columnDragger" onPointerDown={this.columnDividerDown} ref={this._draggerRef} style={{ cursor: this.cursor, left: `${this.columnWidth + this.xMargin}px` }} >
+ <FontAwesomeIcon icon={"arrows-alt-h"} />
</div>;
}
- onContextMenu = (e: React.MouseEvent): void => {
- if (!e.isPropagationStopped() && this.props.Document[Id] !== "mainDoc") { // need to test this because GoldenLayout causes a parallel hierarchy in the React DOM for its children and the main document view7
- ContextMenu.Instance.addItem({
- description: "Toggle multi-column",
- event: () => this.props.Document.singleColumn = !BoolCast(this.props.Document.singleColumn, true), icon: "file-pdf"
- });
- }
- }
@undoBatch
@action
@@ -215,28 +219,40 @@ export class CollectionStackingView extends CollectionSubView(doc => doc) {
}
});
}
- render() {
+ section(heading: string, docList: Doc[]) {
let cols = this.singleColumn ? 1 : Math.max(1, Math.min(this.filteredChildren.length,
Math.floor((this.props.PanelWidth() - 2 * this.xMargin) / (this.columnWidth + this.gridGap))));
let templatecols = "";
for (let i = 0; i < cols; i++) templatecols += `${this.columnWidth}px `;
+ return <div key={heading}>
+ {heading ? <div key={`${heading}`} className="collectionStackingView-sectionHeader">{heading}</div> : (null)}
+ <div key={`${heading}-stack`} className={`collectionStackingView-masonry${this.singleColumn ? "Single" : "Grid"}`}
+ style={{
+ padding: this.singleColumn ? `${this.yMargin}px ${this.xMargin}px ${this.yMargin}px ${this.xMargin}px` : `${this.yMargin}px ${this.xMargin}px`,
+ margin: "auto",
+ width: this.singleColumn ? undefined : `${cols * (this.columnWidth + this.gridGap) + 2 * this.xMargin - this.gridGap}px`,
+ height: 'max-content',
+ position: "relative",
+ gridGap: this.gridGap,
+ gridTemplateColumns: this.singleColumn ? undefined : templatecols,
+ gridAutoRows: this.singleColumn ? undefined : "0px"
+ }}
+ >
+ {this.children(docList)}
+ {this.singleColumn ? (null) : this.columnDragger}
+ </div></div>;
+ }
+ render() {
return (
- <div className="collectionStackingView" ref={this.createRef} onDrop={this.onDrop.bind(this)} onContextMenu={this.onContextMenu} onWheel={(e: React.WheelEvent) => e.stopPropagation()} >
- <div className={`collectionStackingView-masonry${this.singleColumn ? "Single" : "Grid"}`}
- style={{
- padding: this.singleColumn ? `${this.yMargin}px ${this.xMargin}px ${this.yMargin}px ${this.xMargin}px` : `${this.yMargin}px ${this.xMargin}px`,
- margin: "auto",
- width: this.singleColumn ? undefined : `${cols * (this.columnWidth + this.gridGap) + 2 * this.xMargin - this.gridGap}px`,
- height: "100%",
- position: "relative",
- gridGap: this.gridGap,
- gridTemplateColumns: this.singleColumn ? undefined : templatecols,
- gridAutoRows: this.singleColumn ? undefined : `${this._gridSize}px`
- }}
- >
- {this.children}
- {this.singleColumn ? (null) : this.columnDragger}
- </div>
+ <div className="collectionStackingView"
+ ref={this.createRef} onDrop={this.onDrop.bind(this)} onWheel={(e: React.WheelEvent) => e.stopPropagation()} >
+ {/* {sectionFilter as boolean ? [
+ ["width > height", this.filteredChildren.filter(f => f[WidthSym]() >= 1 + f[HeightSym]())],
+ ["width = height", this.filteredChildren.filter(f => Math.abs(f[WidthSym]() - f[HeightSym]()) < 1)],
+ ["height > width", this.filteredChildren.filter(f => f[WidthSym]() + 1 <= f[HeightSym]())]]. */}
+ {this.props.Document.sectionFilter ? Array.from(this.Sections.entries()).
+ map(section => this.section(section[0].toString(), section[1] as Doc[])) :
+ this.section("", this.filteredChildren)}
</div>
);
}
diff --git a/src/client/views/collections/CollectionSubView.tsx b/src/client/views/collections/CollectionSubView.tsx
index 4fd11add4..2ddefb3c0 100644
--- a/src/client/views/collections/CollectionSubView.tsx
+++ b/src/client/views/collections/CollectionSubView.tsx
@@ -9,7 +9,7 @@ import { BoolCast, Cast } from "../../../new_fields/Types";
import { CurrentUserUtils } from "../../../server/authentication/models/current_user_utils";
import { RouteStore } from "../../../server/RouteStore";
import { DocServer } from "../../DocServer";
-import { Docs, DocumentOptions } from "../../documents/Documents";
+import { Docs, DocumentOptions, DocumentType } from "../../documents/Documents";
import { DragManager } from "../../util/DragManager";
import { undoBatch, UndoManager } from "../../util/UndoManager";
import { DocComponent } from "../DocComponent";
@@ -20,6 +20,7 @@ import { CollectionVideoView } from "./CollectionVideoView";
import { CollectionView } from "./CollectionView";
import React = require("react");
import { MainView } from "../MainView";
+import { Utils } from "../../../Utils";
export interface CollectionViewProps extends FieldViewProps {
addDocument: (document: Doc, allowDuplicates?: boolean) => boolean;
@@ -74,7 +75,7 @@ export function CollectionSubView<T>(schemaCtor: (doc: Doc) => T) {
return;
}
// The following conditional detects a recurring bug we've seen on the server
- if (proto[Id] === "collectionProto") {
+ if (proto[Id] === Docs.Prototypes.get(DocumentType.COL)[Id]) {
alert("COLLECTION PROTO CURSOR ISSUE DETECTED! Check console for more info...");
console.log(doc);
console.log(proto);
@@ -164,7 +165,7 @@ export function CollectionSubView<T>(schemaCtor: (doc: Doc) => T) {
} else {
let path = window.location.origin + "/doc/";
if (text.startsWith(path)) {
- let docid = text.replace(DocServer.prepend("/doc/"), "").split("?")[0];
+ let docid = text.replace(Utils.prepend("/doc/"), "").split("?")[0];
DocServer.GetRefField(docid).then(f => {
if (f instanceof Doc) {
if (options.x || options.y) { f.x = options.x; f.y = options.y; } // should be in CollectionFreeFormView
@@ -193,7 +194,7 @@ export function CollectionSubView<T>(schemaCtor: (doc: Doc) => T) {
if (item.kind === "string" && item.type.indexOf("uri") !== -1) {
let str: string;
let prom = new Promise<string>(resolve => e.dataTransfer.items[i].getAsString(resolve))
- .then(action((s: string) => rp.head(DocServer.prepend(RouteStore.corsProxy + "/" + (str = s)))))
+ .then(action((s: string) => rp.head(Utils.CorsProxy(str = s))))
.then(result => {
let type = result["content-type"];
if (type) {
@@ -219,7 +220,7 @@ export function CollectionSubView<T>(schemaCtor: (doc: Doc) => T) {
}).then(async (res: Response) => {
(await res.json()).map(action((file: any) => {
let full = { ...options, nativeWidth: type.indexOf("video") !== -1 ? 600 : 300, width: 300, title: dropFileName };
- let path = DocServer.prepend(file);
+ let path = Utils.prepend(file);
Docs.Get.DocumentFromType(type, path, full).then(doc => doc && this.props.addDocument(doc));
}));
});
diff --git a/src/client/views/collections/CollectionTreeView.tsx b/src/client/views/collections/CollectionTreeView.tsx
index c212cc97c..f98629c5b 100644
--- a/src/client/views/collections/CollectionTreeView.tsx
+++ b/src/client/views/collections/CollectionTreeView.tsx
@@ -1,5 +1,5 @@
import { library } from '@fortawesome/fontawesome-svg-core';
-import { faAngleRight, faCamera, faExpand, faTrash, faBell, faCaretDown, faCaretRight, faCaretSquareDown, faCaretSquareRight, faTrashAlt } from '@fortawesome/free-solid-svg-icons';
+import { faAngleRight, faCamera, faExpand, faTrash, faBell, faCaretDown, faCaretRight, faArrowsAltH, faCaretSquareDown, faCaretSquareRight, faTrashAlt } from '@fortawesome/free-solid-svg-icons';
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
import { action, computed, observable, trace, untracked } from "mobx";
import { observer } from "mobx-react";
@@ -58,6 +58,7 @@ library.add(faCaretDown);
library.add(faCaretRight);
library.add(faCaretSquareDown);
library.add(faCaretSquareRight);
+library.add(faArrowsAltH);
@observer
/**
@@ -73,15 +74,15 @@ class TreeView extends React.Component<TreeViewProps> {
@observable _collapsed: boolean = true;
@computed get fieldKey() {
- let keys = Array.from(Object.keys(this.resolvedDataDoc)); // bcz: Argh -- make untracked to avoid this rerunning whenever 'libraryBrush' is set
- if (this.resolvedDataDoc.proto instanceof Doc) {
- let arr = Array.from(Object.keys(this.resolvedDataDoc.proto));// bcz: Argh -- make untracked to avoid this rerunning whenever 'libraryBrush' is set
+ let keys = Array.from(Object.keys(this.dataDoc)); // bcz: Argh -- make untracked to avoid this rerunning whenever 'libraryBrush' is set
+ if (this.dataDoc.proto instanceof Doc) {
+ let arr = Array.from(Object.keys(this.dataDoc.proto));// bcz: Argh -- make untracked to avoid this rerunning whenever 'libraryBrush' is set
keys.push(...arr);
while (keys.indexOf("proto") !== -1) keys.splice(keys.indexOf("proto"), 1);
}
let keyList: string[] = [];
keys.map(key => {
- let docList = Cast(this.resolvedDataDoc[key], listSpec(Doc));
+ let docList = Cast(this.dataDoc[key], listSpec(Doc));
if (docList && docList.length > 0) {
keyList.push(key);
}
@@ -93,7 +94,16 @@ class TreeView extends React.Component<TreeViewProps> {
return keyList.length ? keyList[0] : "data";
}
- @computed get resolvedDataDoc() { return BoolCast(this.props.document.isTemplate) && this.props.dataDoc ? this.props.dataDoc : this.props.document; }
+ @computed get dataDoc() { return this.resolvedDataDoc ? this.resolvedDataDoc : this.props.document; }
+ @computed get resolvedDataDoc() {
+ if (this.props.dataDoc === undefined && this.props.document.layout instanceof Doc) {
+ // if there is no dataDoc (ie, we're not rendering a template layout), but this document
+ // has a template layout document, then we will render the template layout but use
+ // this document as the data document for the layout.
+ return this.props.document;
+ }
+ return this.props.dataDoc ? this.props.dataDoc : undefined;
+ }
protected createTreeDropTarget = (ele: HTMLDivElement) => {
this._treedropDisposer && this._treedropDisposer();
@@ -102,7 +112,7 @@ class TreeView extends React.Component<TreeViewProps> {
}
}
- @undoBatch delete = () => this.props.deleteDoc(this.resolvedDataDoc);
+ @undoBatch delete = () => this.props.deleteDoc(this.dataDoc);
@undoBatch openRight = async () => this.props.addDocTab(this.props.document, undefined, "onRight");
onPointerDown = (e: React.PointerEvent) => e.stopPropagation();
@@ -134,7 +144,7 @@ class TreeView extends React.Component<TreeViewProps> {
@action
remove = (document: Document, key: string): boolean => {
- let children = Cast(this.resolvedDataDoc[key], listSpec(Doc), []);
+ let children = Cast(this.dataDoc[key], listSpec(Doc), []);
if (children.indexOf(document) !== -1) {
children.splice(children.indexOf(document), 1);
return true;
@@ -150,8 +160,8 @@ class TreeView extends React.Component<TreeViewProps> {
indent = () => this.props.addDocument(this.props.document) && this.delete()
renderBullet() {
- let docList = Cast(this.resolvedDataDoc[this.fieldKey], listSpec(Doc));
- let doc = Cast(this.resolvedDataDoc[this.fieldKey], Doc);
+ let docList = Cast(this.dataDoc[this.fieldKey], listSpec(Doc));
+ let doc = Cast(this.dataDoc[this.fieldKey], Doc);
let isDoc = doc instanceof Doc || docList;
let c;
return <div className="bullet" onClick={action(() => this._collapsed = !this._collapsed)} style={{ color: StrCast(this.props.document.color, "black"), opacity: 0.4 }}>
@@ -163,16 +173,17 @@ class TreeView extends React.Component<TreeViewProps> {
editableView = (key: string, style?: string) => (<EditableView
oneLine={true}
display={"inline"}
- editing={this.resolvedDataDoc[Id] === TreeView.loadId}
+ editing={this.dataDoc[Id] === TreeView.loadId}
contents={StrCast(this.props.document[key])}
height={36}
fontStyle={style}
fontSize={12}
GetValue={() => StrCast(this.props.document[key])}
- SetValue={(value: string) => (Doc.GetProto(this.resolvedDataDoc)[key] = value) ? true : true}
+ SetValue={(value: string) => (Doc.GetProto(this.dataDoc)[key] = value) ? true : true}
OnFillDown={(value: string) => {
- Doc.GetProto(this.resolvedDataDoc)[key] = value;
- let doc = Docs.Create.FreeformDocument([], { title: "", x: 0, y: 0, width: 100, height: 25, templates: new List<string>([Templates.Title.Layout]) });
+ Doc.GetProto(this.dataDoc)[key] = value;
+ let doc = this.props.document.detailedLayout instanceof Doc ? Doc.ApplyTemplate(Doc.GetProto(this.props.document.detailedLayout)) : undefined;
+ if (!doc) doc = Docs.Create.FreeformDocument([], { title: "", x: 0, y: 0, width: 100, height: 25, templates: new List<string>([Templates.Title.Layout]) });
TreeView.loadId = doc[Id];
return this.props.addDocument(doc);
}}
@@ -180,16 +191,16 @@ class TreeView extends React.Component<TreeViewProps> {
/>)
@computed get keyList() {
- let keys = Array.from(Object.keys(this.resolvedDataDoc));
- if (this.resolvedDataDoc.proto instanceof Doc) {
- keys.push(...Array.from(Object.keys(this.resolvedDataDoc.proto)));
+ let keys = Array.from(Object.keys(this.dataDoc));
+ if (this.dataDoc.proto instanceof Doc) {
+ keys.push(...Array.from(Object.keys(this.dataDoc.proto)));
}
let keyList: string[] = keys.reduce((l, key) => {
- let listspec = DocListCast(this.resolvedDataDoc[key]);
+ let listspec = DocListCast(this.dataDoc[key]);
if (listspec && listspec.length) return [...l, key];
return l;
}, [] as string[]);
- keys.map(key => Cast(this.resolvedDataDoc[key], Doc) instanceof Doc && keyList.push(key));
+ keys.map(key => Cast(this.dataDoc[key], Doc) instanceof Doc && (Cast(this.dataDoc[key], Doc) as Doc).type !== undefined && keyList.push(key));
if (LinkManager.Instance.getAllRelatedLinks(this.props.document).length > 0) keyList.push("links");
if (keyList.indexOf(this.fieldKey) !== -1) {
keyList.splice(keyList.indexOf(this.fieldKey), 1);
@@ -202,7 +213,7 @@ class TreeView extends React.Component<TreeViewProps> {
*/
renderTitle() {
let reference = React.createRef<HTMLDivElement>();
- let onItemDown = SetupDrag(reference, () => this.resolvedDataDoc, this.move, this.props.dropAction, this.props.treeViewId, true);
+ let onItemDown = SetupDrag(reference, () => this.dataDoc, this.move, this.props.dropAction, this.props.treeViewId, true);
let headerElements = (
<span className="collectionTreeView-keyHeader" key={this._chosenKey + "chosen"}
@@ -214,7 +225,7 @@ class TreeView extends React.Component<TreeViewProps> {
{this._chosenKey}
</span>);
let dataDocs = CollectionDockingView.Instance ? Cast(CollectionDockingView.Instance.props.Document[this.fieldKey], listSpec(Doc), []) : [];
- let openRight = dataDocs && dataDocs.indexOf(this.resolvedDataDoc) !== -1 ? (null) : (
+ let openRight = dataDocs && dataDocs.indexOf(this.dataDoc) !== -1 ? (null) : (
<div className="treeViewItem-openRight" onPointerDown={this.onPointerDown} onClick={this.openRight}>
<FontAwesomeIcon icon="angle-right" size="lg" />
</div>);
@@ -240,12 +251,12 @@ class TreeView extends React.Component<TreeViewProps> {
if (NumCast(this.props.document.viewType) !== CollectionViewType.Docking) {
ContextMenu.Instance.addItem({ description: "Open Tab", event: () => this.props.addDocTab(this.props.document, this.resolvedDataDoc, "inTab"), icon: "folder" });
ContextMenu.Instance.addItem({ description: "Open Right", event: () => this.props.addDocTab(this.props.document, this.resolvedDataDoc, "onRight"), icon: "caret-square-right" });
- if (DocumentManager.Instance.getDocumentViews(this.resolvedDataDoc).length) {
- ContextMenu.Instance.addItem({ description: "Focus", event: () => DocumentManager.Instance.getDocumentViews(this.resolvedDataDoc).map(view => view.props.focus(this.props.document, true)), icon: "camera" });
+ if (DocumentManager.Instance.getDocumentViews(this.dataDoc).length) {
+ ContextMenu.Instance.addItem({ description: "Focus", event: () => DocumentManager.Instance.getDocumentViews(this.dataDoc).map(view => view.props.focus(this.props.document, true)), icon: "camera" });
}
ContextMenu.Instance.addItem({ description: "Delete Item", event: undoBatch(() => this.props.deleteDoc(this.props.document)), icon: "trash-alt" });
} else {
- ContextMenu.Instance.addItem({ description: "Open as Workspace", event: undoBatch(() => MainView.Instance.openWorkspace(this.resolvedDataDoc)), icon: "caret-square-right" });
+ ContextMenu.Instance.addItem({ description: "Open as Workspace", event: undoBatch(() => MainView.Instance.openWorkspace(this.dataDoc)), icon: "caret-square-right" });
ContextMenu.Instance.addItem({ description: "Delete Workspace", event: undoBatch(() => this.props.deleteDoc(this.props.document)), icon: "trash-alt" });
}
ContextMenu.Instance.addItem({ description: "Open Fields", event: () => { let kvp = Docs.Create.KVPDocument(this.props.document, { width: 300, height: 300 }); this.props.addDocTab(kvp, this.props.dataDoc ? this.props.dataDoc : kvp, "onRight"); }, icon: "layer-group" });
@@ -273,7 +284,7 @@ class TreeView extends React.Component<TreeViewProps> {
if (de.data.draggedDocuments[0] === this.props.document) return true;
let addDoc = (doc: Doc) => this.props.addDocument(doc, this.resolvedDataDoc, before);
if (inside) {
- let docList = Cast(this.resolvedDataDoc.data, listSpec(Doc));
+ let docList = Cast(this.dataDoc.data, listSpec(Doc));
if (docList !== undefined) {
addDoc = (doc: Doc) => { docList && docList.push(doc); return true; };
}
@@ -325,7 +336,7 @@ class TreeView extends React.Component<TreeViewProps> {
@computed get boundsOfCollectionDocument() {
if (StrCast(this.props.document.type).indexOf(DocumentType.COL) === -1) return undefined;
- let layoutDoc = Doc.expandTemplateLayout(this.props.document, this.props.dataDoc);
+ let layoutDoc = this.props.document;
return Doc.ComputeContentBounds(DocListCast(layoutDoc.data));
}
docWidth = () => {
@@ -343,27 +354,30 @@ class TreeView extends React.Component<TreeViewProps> {
})());
}
+ noOverlays = (doc: Doc) => { return { title: "", caption: "" } };
+
render() {
let contentElement: (JSX.Element | null) = null;
- let docList = Cast(this.resolvedDataDoc[this._chosenKey], listSpec(Doc));
+ let docList = Cast(this.dataDoc[this._chosenKey], listSpec(Doc));
let remDoc = (doc: Doc) => this.remove(doc, this._chosenKey);
- let addDoc = (doc: Doc, addBefore?: Doc, before?: boolean) => Doc.AddDocToList(this.resolvedDataDoc, this._chosenKey, doc, addBefore, before);
- let doc = Cast(this.resolvedDataDoc[this._chosenKey], Doc);
+ let addDoc = (doc: Doc, addBefore?: Doc, before?: boolean) => Doc.AddDocToList(this.dataDoc, this._chosenKey, doc, addBefore, before);
+ let doc = Cast(this.dataDoc[this._chosenKey], Doc);
if (!this._collapsed) {
if (!this.props.document.embed) {
contentElement = <ul key={this._chosenKey + "more"}>
{this._chosenKey === "links" ? this.renderLinks() :
- TreeView.GetChildElements(doc instanceof Doc ? [doc] : DocListCast(docList), this.props.treeViewId, this.props.document, this.props.dataDoc, this._chosenKey, addDoc, remDoc, this.move,
+ TreeView.GetChildElements(doc instanceof Doc ? [doc] : DocListCast(docList), this.props.treeViewId, this.props.document, this.resolvedDataDoc, this._chosenKey, addDoc, remDoc, this.move,
this.props.dropAction, this.props.addDocTab, this.props.ScreenToLocalTransform, this.props.outerXf, this.props.active, this.props.panelWidth, this.props.renderDepth)}
</ul >;
} else {
- let layoutDoc = Doc.expandTemplateLayout(this.props.document, this.props.dataDoc);
+ let layoutDoc = this.props.document;
contentElement = <div ref={this._dref} style={{ display: "inline-block", height: this.docHeight() }} key={this.props.document[Id] + this.props.document.title}>
<CollectionSchemaPreview
Document={layoutDoc}
DataDocument={this.resolvedDataDoc}
renderDepth={this.props.renderDepth}
+ showOverlays={this.noOverlays}
fitToBox={this.boundsOfCollectionDocument !== undefined}
width={this.docWidth}
height={this.docHeight}
@@ -546,7 +560,8 @@ export class CollectionTreeView extends CollectionSubView(Document) {
SetValue={(value: string) => (Doc.GetProto(this.resolvedDataDoc).title = value) ? true : true}
OnFillDown={(value: string) => {
Doc.GetProto(this.props.Document).title = value;
- let doc = Docs.Create.FreeformDocument([], { title: "", x: 0, y: 0, width: 100, height: 25, templates: new List<string>([Templates.Title.Layout]) });
+ let doc = this.props.Document.detailedLayout instanceof Doc ? Doc.ApplyTemplate(Doc.GetProto(this.props.Document.detailedLayout)) : undefined;
+ if (!doc) doc = Docs.Create.FreeformDocument([], { title: "", x: 0, y: 0, width: 100, height: 25, templates: new List<string>([Templates.Title.Layout]) });
TreeView.loadId = doc[Id];
Doc.AddDocToList(this.props.Document, this.props.fieldKey, doc, this.childDocs.length ? this.childDocs[0] : undefined, true);
}} />
diff --git a/src/client/views/collections/CollectionVideoView.tsx b/src/client/views/collections/CollectionVideoView.tsx
index d7d5773ba..31a8a93e0 100644
--- a/src/client/views/collections/CollectionVideoView.tsx
+++ b/src/client/views/collections/CollectionVideoView.tsx
@@ -7,6 +7,8 @@ import { CollectionBaseView, CollectionRenderProps, CollectionViewType } from ".
import { CollectionFreeFormView } from "./collectionFreeForm/CollectionFreeFormView";
import "./CollectionVideoView.scss";
import React = require("react");
+import { InkingControl } from "../InkingControl";
+import { InkTool } from "../../../new_fields/InkField";
@observer
@@ -19,18 +21,19 @@ export class CollectionVideoView extends React.Component<FieldViewProps> {
private get uIButtons() {
let scaling = Math.min(1.8, this.props.ScreenToLocalTransform().Scale);
let curTime = NumCast(this.props.Document.curPage);
- return (VideoBox._showControls ? [] : [
- <div className="collectionVideoView-time" key="time" onPointerDown={this.onResetDown} style={{ transform: `scale(${scaling}, ${scaling})` }}>
- <span>{"" + Math.round(curTime)}</span>
- <span style={{ fontSize: 8 }}>{" " + Math.round((curTime - Math.trunc(curTime)) * 100)}</span>
- </div>,
+ return ([<div className="collectionVideoView-time" key="time" onPointerDown={this.onResetDown} style={{ transform: `scale(${scaling}, ${scaling})` }}>
+ <span>{"" + Math.round(curTime)}</span>
+ <span style={{ fontSize: 8 }}>{" " + Math.round((curTime - Math.trunc(curTime)) * 100)}</span>
+ </div>,
+ VideoBox._showControls ? (null) : [
<div className="collectionVideoView-play" key="play" onPointerDown={this.onPlayDown} style={{ transform: `scale(${scaling}, ${scaling})` }}>
{this._videoBox && this._videoBox.Playing ? "\"" : ">"}
</div>,
<div className="collectionVideoView-full" key="full" onPointerDown={this.onFullDown} style={{ transform: `scale(${scaling}, ${scaling})` }}>
F
</div>
- ]);
+
+ ]]);
}
@action
@@ -53,12 +56,33 @@ export class CollectionVideoView extends React.Component<FieldViewProps> {
}
}
+ _isclick = 0;
@action
- onResetDown = () => {
+ onResetDown = (e: React.PointerEvent) => {
if (this._videoBox) {
this._videoBox.Pause();
- this.props.Document.curPage = 0;
+ e.stopPropagation();
+ this._isclick = 0;
+ document.addEventListener("pointermove", this.onPointerMove, true);
+ document.addEventListener("pointerup", this.onPointerUp, true);
+ InkingControl.Instance.switchTool(InkTool.Eraser);
+ }
+ }
+
+ @action
+ onPointerMove = (e: PointerEvent) => {
+ this._isclick += Math.abs(e.movementX) + Math.abs(e.movementY);
+ if (this._videoBox) {
+ this._videoBox.Seek(Math.max(0, NumCast(this.props.Document.curPage, 0) + Math.sign(e.movementX) * 0.0333));
}
+ e.stopImmediatePropagation();
+ }
+ @action
+ onPointerUp = (e: PointerEvent) => {
+ document.removeEventListener("pointermove", this.onPointerMove, true);
+ document.removeEventListener("pointerup", this.onPointerUp, true);
+ InkingControl.Instance.switchTool(InkTool.None);
+ this._isclick < 10 && (this.props.Document.curPage = 0);
}
setVideoBox = (videoBox: VideoBox) => { this._videoBox = videoBox; };
diff --git a/src/client/views/collections/CollectionView.tsx b/src/client/views/collections/CollectionView.tsx
index 56750668d..4a51a1f58 100644
--- a/src/client/views/collections/CollectionView.tsx
+++ b/src/client/views/collections/CollectionView.tsx
@@ -1,11 +1,10 @@
import { library } from '@fortawesome/fontawesome-svg-core';
-import { faProjectDiagram, faSignature, faSquare, faTh, faThList, faTree } from '@fortawesome/free-solid-svg-icons';
+import { faProjectDiagram, faSignature, faColumns, faSquare, faTh, faImage, faThList, faTree, faEllipsisV } from '@fortawesome/free-solid-svg-icons';
import { observer } from "mobx-react";
import * as React from 'react';
-import { Doc } from '../../../new_fields/Doc';
+import { Doc, DocListCast, WidthSym, HeightSym } from '../../../new_fields/Doc';
import { Id } from '../../../new_fields/FieldSymbols';
import { CurrentUserUtils } from '../../../server/authentication/models/current_user_utils';
-import { Docs } from '../../documents/Documents';
import { undoBatch } from '../../util/UndoManager';
import { ContextMenu } from "../ContextMenu";
import { ContextMenuProps } from '../ContextMenuItem';
@@ -16,6 +15,8 @@ import { CollectionFreeFormView } from './collectionFreeForm/CollectionFreeFormV
import { CollectionSchemaView } from "./CollectionSchemaView";
import { CollectionStackingView } from './CollectionStackingView';
import { CollectionTreeView } from "./CollectionTreeView";
+import { StrCast, PromiseValue } from '../../../new_fields/Types';
+import { DocumentType } from '../../documents/Documents';
export const COLLECTION_BORDER_WIDTH = 2;
library.add(faTh);
@@ -24,6 +25,9 @@ library.add(faSquare);
library.add(faProjectDiagram);
library.add(faSignature);
library.add(faThList);
+library.add(faColumns);
+library.add(faEllipsisV);
+library.add(faImage);
@observer
export class CollectionView extends React.Component<FieldViewProps> {
@@ -35,7 +39,8 @@ export class CollectionView extends React.Component<FieldViewProps> {
case CollectionViewType.Schema: return (<CollectionSchemaView {...props} CollectionView={this} />);
case CollectionViewType.Docking: return (<CollectionDockingView {...props} CollectionView={this} />);
case CollectionViewType.Tree: return (<CollectionTreeView {...props} CollectionView={this} />);
- case CollectionViewType.Stacking: return (<CollectionStackingView {...props} CollectionView={this} />);
+ case CollectionViewType.Stacking: { this.props.Document.singleColumn = true; return (<CollectionStackingView {...props} CollectionView={this} />); }
+ case CollectionViewType.Masonry: { this.props.Document.singleColumn = false; return (<CollectionStackingView {...props} CollectionView={this} />); }
case CollectionViewType.Freeform:
default:
return (<CollectionFreeFormView {...props} CollectionView={this} />);
@@ -54,18 +59,10 @@ export class CollectionView extends React.Component<FieldViewProps> {
}
subItems.push({ description: "Schema", event: undoBatch(() => this.props.Document.viewType = CollectionViewType.Schema), icon: "th-list" });
subItems.push({ description: "Treeview", event: undoBatch(() => this.props.Document.viewType = CollectionViewType.Tree), icon: "tree" });
- subItems.push({ description: "Stacking", event: undoBatch(() => this.props.Document.viewType = CollectionViewType.Stacking), icon: "th-list" });
+ subItems.push({ description: "Stacking", event: undoBatch(() => this.props.Document.viewType = CollectionViewType.Stacking), icon: "ellipsis-v" });
+ subItems.push({ description: "Masonry", event: undoBatch(() => this.props.Document.viewType = CollectionViewType.Masonry), icon: "columns" });
ContextMenu.Instance.addItem({ description: "View Modes...", subitems: subItems });
- ContextMenu.Instance.addItem({
- description: "Apply Template", event: undoBatch(() => {
- let otherdoc = new Doc();
- otherdoc.width = 100;
- otherdoc.height = 50;
- Doc.GetProto(otherdoc).title = "applied(" + this.props.Document.title + ")";
- Doc.GetProto(otherdoc).layout = Doc.MakeDelegate(this.props.Document);
- this.props.addDocTab && this.props.addDocTab(otherdoc, undefined, "onRight");
- }), icon: "project-diagram"
- });
+ ContextMenu.Instance.addItem({ description: "Apply Template", event: undoBatch(() => this.props.addDocTab && this.props.addDocTab(Doc.ApplyTemplate(this.props.Document)!, undefined, "onRight")), icon: "project-diagram" });
}
}
diff --git a/src/client/views/collections/collectionFreeForm/CollectionFreeFormView.tsx b/src/client/views/collections/collectionFreeForm/CollectionFreeFormView.tsx
index b91aaedee..6bb082b66 100644
--- a/src/client/views/collections/collectionFreeForm/CollectionFreeFormView.tsx
+++ b/src/client/views/collections/collectionFreeForm/CollectionFreeFormView.tsx
@@ -4,7 +4,7 @@ import { Doc, DocListCastAsync, HeightSym, WidthSym, DocListCast } from "../../.
import { Id } from "../../../../new_fields/FieldSymbols";
import { InkField, StrokeData } from "../../../../new_fields/InkField";
import { createSchema, makeInterface } from "../../../../new_fields/Schema";
-import { BoolCast, Cast, FieldValue, NumCast } from "../../../../new_fields/Types";
+import { BoolCast, Cast, FieldValue, NumCast, StrCast } from "../../../../new_fields/Types";
import { emptyFunction, returnOne } from "../../../../Utils";
import { DocumentManager } from "../../../util/DocumentManager";
import { DragManager } from "../../../util/DragManager";
@@ -195,10 +195,10 @@ export class CollectionFreeFormView extends CollectionSubView(PanZoomDocument) {
this._pheight / this.zoomScaling());
let panelwidth = panelDim[0];
let panelheight = panelDim[1];
- if (ranges[0][0] - dx > (this.panX() + panelwidth / 2)) x = ranges[0][1] + panelwidth / 2;
- if (ranges[0][1] - dx < (this.panX() - panelwidth / 2)) x = ranges[0][0] - panelwidth / 2;
- if (ranges[1][0] - dy > (this.panY() + panelheight / 2)) y = ranges[1][1] + panelheight / 2;
- if (ranges[1][1] - dy < (this.panY() - panelheight / 2)) y = ranges[1][0] - panelheight / 2;
+ // if (ranges[0][0] - dx > (this.panX() + panelwidth / 2)) x = ranges[0][1] + panelwidth / 2;
+ // if (ranges[0][1] - dx < (this.panX() - panelwidth / 2)) x = ranges[0][0] - panelwidth / 2;
+ // if (ranges[1][0] - dy > (this.panY() + panelheight / 2)) y = ranges[1][1] + panelheight / 2;
+ // if (ranges[1][1] - dy < (this.panY() - panelheight / 2)) y = ranges[1][0] - panelheight / 2;
}
this.setPan(x - dx, y - dy);
this._lastX = e.pageX;
@@ -263,7 +263,7 @@ export class CollectionFreeFormView extends CollectionSubView(PanZoomDocument) {
const newPanX = Math.min((1 - 1 / scale) * this.nativeWidth, Math.max(0, panX));
const newPanY = Math.min((1 - 1 / scale) * this.nativeHeight, Math.max(0, panY));
this.props.Document.panX = this.isAnnotationOverlay ? newPanX : panX;
- this.props.Document.panY = this.isAnnotationOverlay ? newPanY : panY;
+ this.props.Document.panY = this.isAnnotationOverlay && StrCast(this.props.Document.backgroundLayout).indexOf("PDFBox") === -1 ? newPanY : panY;
// this.props.Document.panX = panX;
// this.props.Document.panY = panY;
if (this.props.Document.scrollY) {
@@ -358,6 +358,7 @@ export class CollectionFreeFormView extends CollectionSubView(PanZoomDocument) {
getChildDocumentViewProps(childDocLayout: Doc): DocumentViewProps {
let self = this;
let resolvedDataDoc = !this.props.Document.isTemplate && this.props.DataDoc !== this.props.Document ? this.props.DataDoc : undefined;
+ resolvedDataDoc && Doc.UpdateDocumentExtensionForField(resolvedDataDoc, this.props.fieldKey);
let layoutDoc = Doc.expandTemplateLayout(childDocLayout, resolvedDataDoc);
return {
DataDoc: resolvedDataDoc !== layoutDoc && resolvedDataDoc ? resolvedDataDoc : undefined,
@@ -502,10 +503,10 @@ export class CollectionFreeFormView extends CollectionSubView(PanZoomDocument) {
overlayDisposer();
setTimeout(() => docs.map(d => d.transition = undefined), 1200);
}} />;
- overlayDisposer = OverlayView.Instance.addElement(scriptingBox, options);
+ overlayDisposer = OverlayView.Instance.addWindow(scriptingBox, options);
};
- addOverlay("arrangeInit", { x: 400, y: 100, width: 400, height: 300 }, { collection: "Doc", docs: "Doc[]" }, undefined);
- addOverlay("arrangeScript", { x: 400, y: 500, width: 400, height: 300 }, { doc: "Doc", index: "number", collection: "Doc", state: "any", docs: "Doc[]" }, "{x: number, y: number, width?: number, height?: number}");
+ addOverlay("arrangeInit", { x: 400, y: 100, width: 400, height: 300, title: "Layout Initialization" }, { collection: "Doc", docs: "Doc[]" }, undefined);
+ addOverlay("arrangeScript", { x: 400, y: 500, width: 400, height: 300, title: "Layout Script" }, { doc: "Doc", index: "number", collection: "Doc", state: "any", docs: "Doc[]" }, "{x: number, y: number, width?: number, height?: number}");
}
});
}