diff options
Diffstat (limited to 'src/client/views')
| -rw-r--r-- | src/client/views/DocumentDecorations.tsx | 11 | ||||
| -rw-r--r-- | src/client/views/Main.tsx | 176 | ||||
| -rw-r--r-- | src/client/views/collections/CollectionDockingView.tsx | 84 | ||||
| -rw-r--r-- | src/client/views/collections/CollectionFreeFormView.tsx | 41 | ||||
| -rw-r--r-- | src/client/views/collections/CollectionSchemaView.tsx | 8 | ||||
| -rw-r--r-- | src/client/views/collections/CollectionViewBase.tsx | 2 | ||||
| -rw-r--r-- | src/client/views/nodes/CollectionFreeFormDocumentView.tsx | 3 | ||||
| -rw-r--r-- | src/client/views/nodes/DocumentView.tsx | 50 | ||||
| -rw-r--r-- | src/client/views/nodes/FieldView.tsx | 2 | ||||
| -rw-r--r-- | src/client/views/nodes/FormattedTextBox.tsx | 2 | ||||
| -rw-r--r-- | src/client/views/nodes/ImageBox.tsx | 8 |
11 files changed, 259 insertions, 128 deletions
diff --git a/src/client/views/DocumentDecorations.tsx b/src/client/views/DocumentDecorations.tsx index d385bcdef..48f5f01a1 100644 --- a/src/client/views/DocumentDecorations.tsx +++ b/src/client/views/DocumentDecorations.tsx @@ -4,7 +4,7 @@ import { SelectionManager } from "../util/SelectionManager"; import { observer } from "mobx-react"; import './DocumentDecorations.scss' import { CollectionFreeFormView } from "./collections/CollectionFreeFormView"; -import { KeyStore } from '../../fields/Key' +import { KeyStore } from '../../fields/KeyStore' import { NumberField } from "../../fields/NumberField"; @observer @@ -127,16 +127,14 @@ export class DocumentDecorations extends React.Component { let width = doc.GetOrCreate(KeyStore.Width, NumberField); let height = doc.GetOrCreate(KeyStore.Height, NumberField); let x = doc.GetOrCreate(KeyStore.X, NumberField); - let y = doc.GetOrCreate(KeyStore.X, NumberField); + let y = doc.GetOrCreate(KeyStore.Y, NumberField); let scale = width.Data / rect.width; let actualdW = Math.max(width.Data + (dW * scale), 20); let actualdH = Math.max(height.Data + (dH * scale), 20); x.Data += dX * (actualdW - width.Data); y.Data += dY * (actualdH - height.Data); - if (Math.abs(dW) > Math.abs(dH)) - width.Data = actualdW; - else - height.Data = actualdH; + width.Data = actualdW; + height.Data = actualdH; } }) } @@ -170,7 +168,6 @@ export class DocumentDecorations extends React.Component { <div id="documentDecorations-bottomLeftResizer" className="documentDecorations-resizer" onPointerDown={this.onPointerDown} onContextMenu={(e) => e.preventDefault()}></div> <div id="documentDecorations-bottomResizer" className="documentDecorations-resizer" onPointerDown={this.onPointerDown} onContextMenu={(e) => e.preventDefault()}></div> <div id="documentDecorations-bottomRightResizer" className="documentDecorations-resizer" onPointerDown={this.onPointerDown} onContextMenu={(e) => e.preventDefault()}></div> - </div> ) } diff --git a/src/client/views/Main.tsx b/src/client/views/Main.tsx index a86fdb9b0..f44ad0a74 100644 --- a/src/client/views/Main.tsx +++ b/src/client/views/Main.tsx @@ -1,28 +1,26 @@ -import { action, configure } from 'mobx'; +import { action, configure, reaction, computed } from 'mobx'; import "normalize.css"; import * as React from 'react'; import * as ReactDOM from 'react-dom'; import { DocumentDecorations } from './DocumentDecorations'; import { Documents } from '../documents/Documents'; import { Document } from '../../fields/Document'; -import { KeyStore, KeyStore as KS } from '../../fields/Key'; -import { ListField } from '../../fields/ListField'; -import { NumberField } from '../../fields/NumberField'; -import { TextField } from '../../fields/TextField'; +import { KeyStore } from '../../fields/KeyStore'; import "./Main.scss"; import { ContextMenu } from './ContextMenu'; import { DocumentView } from './nodes/DocumentView'; -import { ImageField } from '../../fields/ImageField'; +import { Server } from '../Server'; +import { Utils } from '../../Utils'; +import { ServerUtils } from '../../server/ServerUtil'; +import { MessageStore, DocumentTransfer } from '../../server/Message'; import { Transform } from '../util/Transform'; import { CollectionDockingView } from './collections/CollectionDockingView'; +import { FieldWaiting } from '../../fields/Field'; configure({ enforceActions: "observed" }); - -const mainNodeCollection = new Array<Document>(); - window.addEventListener("drop", function (e) { e.preventDefault(); }, false) @@ -36,50 +34,124 @@ document.addEventListener("pointerdown", action(function (e: PointerEvent) { }), true) -let doc1 = Documents.TextDocument({ title: "hello", width: 400, height: 300 }); -let doc2 = doc1.MakeDelegate(); -doc2.Set(KS.X, new NumberField(150)); -doc2.Set(KS.Y, new NumberField(20)); -let doc3 = Documents.ImageDocument("https://psmag.com/.image/t_share/MTMyNzc2NzM1MDY1MjgzMDM4/shutterstock_151341212jpg.jpg", { - x: 450, y: 100, title: "dog", width: 606, height: 386, nativeWidth: 606, nativeHeight: 386 -}); -//doc3.Set(KeyStore.Data, new ImageField); -const schemaDocs = Array.from(Array(5).keys()).map(v => Documents.ImageDocument("https://psmag.com/.image/t_share/MTMyNzc2NzM1MDY1MjgzMDM4/shutterstock_151341212jpg.jpg", { - x: 50 + 100 * v, y: 50, width: 100, height: 100, title: "cat" + v, nativeWidth: 606, nativeHeight: 386 -})); -schemaDocs.push(doc3); -schemaDocs[0].SetData(KS.Author, "Tyler", TextField); -schemaDocs[4].SetData(KS.Author, "Bob", TextField); -schemaDocs.push(doc2); -const doc7 = Documents.SchemaDocument(schemaDocs) -const docset = [doc1, doc2, doc3, doc7]; -let doc4 = Documents.CollectionDocument(docset, { - x: 0, y: 400, title: "mini collection" +//runInAction(() => +// let doc1 = Documents.TextDocument({ title: "hello" }); +// let doc2 = doc1.MakeDelegate(); +// doc2.Set(KS.X, new NumberField(150)); +// doc2.Set(KS.Y, new NumberField(20)); +// let doc3 = Documents.ImageDocument("https://upload.wikimedia.org/wikipedia/commons/thumb/3/3a/Cat03.jpg/1200px-Cat03.jpg", { +// x: 450, y: 100, title: "cat 1" +// }); +// doc3.Set(KeyStore.Data, new ImageField); +// const schemaDocs = Array.from(Array(5).keys()).map(v => Documents.ImageDocument("https://upload.wikimedia.org/wikipedia/commons/thumb/3/3a/Cat03.jpg/1200px-Cat03.jpg", { +// x: 50 + 100 * v, y: 50, width: 100, height: 100, title: "cat" + v +// })); +// schemaDocs[0].SetData(KS.Author, "Tyler", TextField); +// schemaDocs[4].SetData(KS.Author, "Bob", TextField); +// schemaDocs.push(doc2); +// const doc7 = Documents.SchemaDocument(schemaDocs) + +const mainDocId = "mainDoc"; +Documents.initProtos(() => { + Utils.EmitCallback(Server.Socket, MessageStore.GetField, mainDocId, (res: any) => { + console.log("HELLO WORLD") + console.log("RESPONSE: " + res) + let mainContainer: Document; + let mainfreeform: Document; + if (res) { + mainContainer = ServerUtils.FromJson(res) as Document; + var mainfreeformid = mainContainer._proxies.get(KeyStore.ActiveFrame.Id)!; + Server.GetField(mainfreeformid, (field) => { + if (field) { + mainfreeform = field as Document; + } + }) + mainfreeform = mainContainer.Get(KeyStore.ActiveFrame) as Document; + } + else { + mainfreeform = Documents.CollectionDocument([], { x: 0, y: 400, title: "mini collection" }); + Utils.Emit(Server.Socket, MessageStore.AddDocument, new DocumentTransfer(mainfreeform.ToJson())); + + var docs = [mainfreeform].map(doc => CollectionDockingView.makeDocumentConfig(doc)); + var config = { settings: { selectionEnabled: false }, content: [{ type: 'row', content: docs }] }; + mainContainer = Documents.DockDocument(JSON.stringify(config), { title: "main container" }, mainDocId); + Utils.Emit(Server.Socket, MessageStore.AddDocument, new DocumentTransfer(mainContainer.ToJson())) + mainContainer.Set(KeyStore.ActiveFrame, mainfreeform); + } + + let addImageNode = action(() => { + mainfreeform.GetList<Document>(KeyStore.Data, []).push(Documents.ImageDocument("https://upload.wikimedia.org/wikipedia/commons/thumb/3/3a/Cat03.jpg/1200px-Cat03.jpg", { + x: 0, y: 300, width: 200, height: 200, title: "added note" + })); + }) + let addTextNode = action(() => { + mainfreeform.GetList<Document>(KeyStore.Data, []).push(Documents.TextDocument({ + x: 0, y: 300, width: 200, height: 200, title: "added note" + })); + }) + let addColNode = action(() => { + mainfreeform.GetList<Document>(KeyStore.Data, []).push(Documents.CollectionDocument([], { + x: 0, y: 300, width: 200, height: 200, title: "added note" + })); + }) + + let clearDatabase = action(() => { + Utils.Emit(Server.Socket, MessageStore.DeleteAll, {}); + }) + + ReactDOM.render(( + <div style={{ position: "absolute", width: "100%", height: "100%" }}> + <DocumentView Document={mainContainer} + AddDocument={undefined} RemoveDocument={undefined} ScreenToLocalTransform={() => Transform.Identity} + Scaling={1} + isTopMost={true} + ContainingCollectionView={undefined} /> + <DocumentDecorations /> + <ContextMenu /> + <button style={{ + position: 'absolute', + bottom: '0px', + left: '0px', + width: '150px' + }} onClick={addImageNode}>Add Image</button> + <button style={{ + position: 'absolute', + bottom: '25px', + left: '0px', + width: '150px' + }} onClick={addTextNode}>Add Text</button> + <button style={{ + position: 'absolute', + bottom: '50px', + left: '0px', + width: '150px' + }} onClick={addColNode}>Add Collection</button> + <button style={{ + position: 'absolute', + bottom: '75px', + left: '0px', + width: '150px' + }} onClick={clearDatabase}>Clear Database</button> + </div>), + document.getElementById('root')); + }) }); // let doc5 = Documents.ImageDocument("https://upload.wikimedia.org/wikipedia/commons/thumb/3/3a/Cat03.jpg/1200px-Cat03.jpg", { // x: 650, y: 500, width: 600, height: 600, title: "cat 2" // }); -let docset2 = [doc3, doc4, doc2]; -let doc6 = Documents.CollectionDocument(docset2, { - x: 350, y: 100, width: 600, height: 600, title: "docking collection" -}); - -var docs = [doc4, doc3, doc6].map(doc => CollectionDockingView.makeDocumentConfig(doc)); -var config = { - settings: { selectionEnabled: false }, content: [{ type: 'row', content: docs }] -}; -let mainContainer = Documents.DockDocument(JSON.stringify(config), { - x: 0, y: 0, title: "main container" -}) - -ReactDOM.render(( - <div style={{ position: "absolute", width: "100%", height: "100%" }}> - <DocumentView Document={mainContainer} - AddDocument={undefined} RemoveDocument={undefined} ScreenToLocalTransform={() => Transform.Identity} - Scaling={1} - isTopMost={true} - ContainingCollectionView={undefined} /> - <DocumentDecorations /> - <ContextMenu /> - </div>), - document.getElementById('root'));
\ No newline at end of file +// let docset2 = new Array<Document>(doc4);//, doc1, doc3); +// let doc6 = Documents.CollectionDocument(docset2, { +// x: 350, y: 100, width: 600, height: 600, title: "docking collection" +// }); +// let mainNodes = mainContainer.GetOrCreate(KeyStore.Data, ListField); +// mainNodes.Data.push(doc6); +// mainNodes.Data.push(doc2); +// mainNodes.Data.push(doc4); +// mainNodes.Data.push(doc3); +// mainNodes.Data.push(doc5); +// mainNodes.Data.push(doc1); +//mainNodes.Data.push(doc2); +//mainNodes.Data.push(doc6); +// mainContainer.Set(KeyStore.Data, mainNodes); +//} +//); diff --git a/src/client/views/collections/CollectionDockingView.tsx b/src/client/views/collections/CollectionDockingView.tsx index 885a4bece..41fad9dac 100644 --- a/src/client/views/collections/CollectionDockingView.tsx +++ b/src/client/views/collections/CollectionDockingView.tsx @@ -1,21 +1,23 @@ import * as GoldenLayout from "golden-layout"; import 'golden-layout/src/css/goldenlayout-base.css'; import 'golden-layout/src/css/goldenlayout-dark-theme.css'; -import { action, computed, reaction, observable } from "mobx"; -import { observer } from "mobx-react"; -import { Document } from "../../../fields/Document"; -import { KeyStore } from "../../../fields/Key"; -import { ListField } from "../../../fields/ListField"; +import { action, computed, observable, reaction } from "mobx"; import { DragManager } from "../../util/DragManager"; import { DocumentView } from "../nodes/DocumentView"; +import { Document } from "../../../fields/Document"; import "./CollectionDockingView.scss"; -import { CollectionViewBase, CollectionViewProps, COLLECTION_BORDER_WIDTH } from "./CollectionViewBase"; +import { CollectionViewBase, COLLECTION_BORDER_WIDTH, CollectionViewProps } from "./CollectionViewBase"; import React = require("react"); import * as ReactDOM from 'react-dom'; import Measure from "react-measure"; import { Utils } from "../../../Utils"; -import { FieldId } from "../../../fields/Field"; +import { FieldId, FieldWaiting, Field } from "../../../fields/Field"; import { Server } from "../../Server"; +import { observer } from "mobx-react"; +import { ListField } from "../../../fields/ListField"; +import { KeyStore } from "../../../fields/KeyStore"; +import { Opt } from "../../../fields/Field"; +import { TextField } from "../../../fields/TextField"; @observer export class CollectionDockingView extends CollectionViewBase { @@ -94,13 +96,7 @@ export class CollectionDockingView extends CollectionViewBase { var newContentItem = new this._goldenLayout._typeToItem[newItemStackConfig.type](this._goldenLayout, newItemStackConfig, parent); if (this._goldenLayout.root.contentItems[0].isRow) { - var rowlayout = this._goldenLayout.root.contentItems[0]; - var lastRowItem = rowlayout.contentItems[rowlayout.contentItems.length - 1]; - - lastRowItem.config["width"] *= 0.5; - newContentItem.config["width"] = lastRowItem.config["width"]; - rowlayout.addChild(newContentItem, rowlayout.contentItems.length, true); - rowlayout.callDownwards('setSize'); + this._goldenLayout.root.contentItems[0].addChild(newContentItem); } else { var collayout = this._goldenLayout.root.contentItems[0]; @@ -116,15 +112,32 @@ export class CollectionDockingView extends CollectionViewBase { } } - componentDidMount: () => void = () => { - if (this._containerRef.current) { - - this._goldenLayout = new GoldenLayout(JSON.parse(this.props.Document.GetText(KeyStore.Data, ""))); + setupGoldenLayout() { + var config = this.props.Document.GetText(KeyStore.Data, ""); + if (config) { + if (!this._goldenLayout) + this._goldenLayout = new GoldenLayout(JSON.parse(config)); + else { + this._goldenLayout.destroy(); + this._goldenLayout = new GoldenLayout(JSON.parse(config)); + } this._goldenLayout.on('tabCreated', this.tabCreated); this._goldenLayout.on('stackCreated', this.stackCreated); this._goldenLayout.registerComponent('DocumentFrameRenderer', DockedFrameRenderer); this._goldenLayout.container = this._containerRef.current; this._goldenLayout.init(); + this._goldenLayout.on('stateChanged', this.stateChanged); + } + } + componentDidMount: () => void = () => { + if (this._containerRef.current) { + reaction(() => { + if (this.props.Document.Get(KeyStore.Data) as TextField) { + return [(this.props.Document.Get(KeyStore.Data) as TextField).Data]; + } + return [this.props.Document.Get(KeyStore.Data)]; + }, () => this.setupGoldenLayout()); // should only react once when the Data field is retrieved from the sever .. after that, changes to the Data field will not trigger this reaction. + this.setupGoldenLayout(); window.addEventListener('resize', this.onResize); // bcz: would rather add this event to the parent node, but resize events only come from Window } @@ -152,21 +165,23 @@ export class CollectionDockingView extends CollectionViewBase { } } + stateChanged = () => { + var json = JSON.stringify(this._goldenLayout.toConfig()); + this.props.Document.SetText(KeyStore.Data, json) + } + tabCreated = (tab: any) => { - { - if (this._dragDiv) { - this._dragDiv.removeChild(this._dragElement); - this._dragParent!.removeChild(this._dragFakeElement!); - this._dragParent!.appendChild(this._dragElement!); - DragManager.Root().removeChild(this._dragDiv); - this._dragDiv = null; - } - //tab.setTitle(tab.contentItem.config.componentState.title); - tab.closeElement.off('click') //unbind the current click handler - .click(function () { - tab.contentItem.remove(); - }); + if (this._dragDiv) { + this._dragDiv.removeChild(this._dragElement); + this._dragParent!.removeChild(this._dragFakeElement!); + this._dragParent!.appendChild(this._dragElement!); + DragManager.Root().removeChild(this._dragDiv); + this._dragDiv = null; } + tab.closeElement.off('click') //unbind the current click handler + .click(function () { + tab.contentItem.remove(); + }); } stackCreated = (stack: any) => { @@ -216,15 +231,18 @@ export class DockedFrameRenderer extends React.Component<DockedFrameProps> { private _mainCont = React.createRef<HTMLDivElement>(); constructor(props: any) { super(props); + Server.GetField(this.props.documentId, (f) => { this.Document = f as Document; }) } @observable private _parentScaling = 1; // used to transfer the dimensions of the content pane in the DOM to the ParentScaling prop of the DocumentView - @computed - private get Document() { return Server.GetField(this.props.documentId, () => { }) as Document } + @observable + private Document: Opt<Document>; render() { + if (!this.Document) + return <div></div> let nativeWidth = this.Document.GetNumber(KeyStore.NativeWidth, 0); var layout = this.Document.GetText(KeyStore.Layout, ""); var content = diff --git a/src/client/views/collections/CollectionFreeFormView.tsx b/src/client/views/collections/CollectionFreeFormView.tsx index 2c0a3f478..1f15069fd 100644 --- a/src/client/views/collections/CollectionFreeFormView.tsx +++ b/src/client/views/collections/CollectionFreeFormView.tsx @@ -1,13 +1,11 @@ import { observer } from "mobx-react"; import React = require("react"); -import { action, observable, computed } from "mobx"; +import { action, computed } from "mobx"; import { CollectionFreeFormDocumentView } from "../nodes/CollectionFreeFormDocumentView"; import { DragManager } from "../../util/DragManager"; import "./CollectionFreeFormView.scss"; -import { Utils } from "../../../Utils"; -import { CollectionViewBase, CollectionViewProps, COLLECTION_BORDER_WIDTH } from "./CollectionViewBase"; -import { SelectionManager } from "../../util/SelectionManager"; -import { Key, KeyStore } from "../../../fields/Key"; +import { CollectionViewBase, COLLECTION_BORDER_WIDTH } from "./CollectionViewBase"; +import { KeyStore } from "../../../fields/KeyStore"; import { Document } from "../../../fields/Document"; import { ListField } from "../../../fields/ListField"; import { NumberField } from "../../../fields/NumberField"; @@ -19,17 +17,12 @@ import { DocumentView } from "../nodes/DocumentView"; @observer export class CollectionFreeFormView extends CollectionViewBase { public static LayoutString(fieldKey: string = "DataKey") { return CollectionViewBase.LayoutString("CollectionFreeFormView", fieldKey); } - private _containerRef = React.createRef<HTMLDivElement>(); private _canvasRef = React.createRef<HTMLDivElement>(); private _lastX: number = 0; private _lastY: number = 0; private _downX: number = 0; private _downY: number = 0; - constructor(props: CollectionViewProps) { - super(props); - } - @computed get isAnnotationOverlay() { return this.props.fieldKey == KeyStore.Annotations; } @@ -65,9 +58,13 @@ export class CollectionFreeFormView extends CollectionViewBase { e.stopPropagation(); } - componentDidMount() { - if (this._containerRef.current) { - DragManager.MakeDropTarget(this._containerRef.current, { + private dropDisposer?: DragManager.DragDropDisposer; + createDropTarget = (ele: HTMLDivElement) => { + if (this.dropDisposer) { + this.dropDisposer(); + } + if (ele) { + this.dropDisposer = DragManager.MakeDropTarget(ele, { handlers: { drop: this.drop } @@ -119,7 +116,6 @@ export class CollectionFreeFormView extends CollectionViewBase { onPointerWheel = (e: React.WheelEvent): void => { e.stopPropagation(); e.preventDefault(); - let modes = ['pixels', 'lines', 'page']; let coefficient = 1000; // if (modes[e.deltaMode] == 'pixels') coefficient = 50; // else if (modes[e.deltaMode] == 'lines') coefficient = 1000; // This should correspond to line-height?? @@ -155,7 +151,7 @@ export class CollectionFreeFormView extends CollectionViewBase { let x = e.pageX - panx let y = e.pageY - pany - fReader.addEventListener("load", action("drop", (event) => { + fReader.addEventListener("load", action("drop", () => { if (fReader.result) { let url = "" + fReader.result; let doc = Documents.ImageDocument(url, { @@ -177,7 +173,7 @@ export class CollectionFreeFormView extends CollectionViewBase { } } - onDragOver = (e: React.DragEvent): void => { + onDragOver = (): void => { } @action @@ -220,11 +216,14 @@ export class CollectionFreeFormView extends CollectionViewBase { } render() { - const Document: Document = this.props.Document; - const value: Document[] = Document.GetList<Document>(this.props.fieldKey, []); + const { fieldKey, Document } = this.props; + // const value: Document[] = Document.GetList<Document>(fieldKey, []); + const lvalue = Document.GetT<ListField<Document>>(fieldKey, ListField); + if (!lvalue || lvalue === "<Waiting>") { + return <p>Error loading collection data</p> + } const panx: number = Document.GetNumber(KeyStore.PanX, 0); const pany: number = Document.GetNumber(KeyStore.PanY, 0); - var me = this; return ( <div className="collectionfreeformview-container" @@ -236,13 +235,13 @@ export class CollectionFreeFormView extends CollectionViewBase { style={{ borderWidth: `${COLLECTION_BORDER_WIDTH}px`, }} - ref={this._containerRef}> + ref={this.createDropTarget}> <div className="collectionfreeformview" style={{ width: "100%", transformOrigin: "left top", transform: ` translate(${panx}px, ${pany}px) scale(${this.zoomScaling}, ${this.zoomScaling})` }} ref={this._canvasRef}> {this.props.BackgroundView ? this.props.BackgroundView() : null} - {value.map(doc => { + {lvalue.Data.map(doc => { return (<CollectionFreeFormDocumentView key={doc.Id} Document={doc} AddDocument={this.addDocument} RemoveDocument={this.removeDocument} diff --git a/src/client/views/collections/CollectionSchemaView.tsx b/src/client/views/collections/CollectionSchemaView.tsx index 5c95aca99..719783fd7 100644 --- a/src/client/views/collections/CollectionSchemaView.tsx +++ b/src/client/views/collections/CollectionSchemaView.tsx @@ -11,7 +11,7 @@ import { CollectionViewBase, COLLECTION_BORDER_WIDTH } from "./CollectionViewBas import { DocumentView } from "../nodes/DocumentView"; import { EditableView } from "../EditableView"; import { CompileScript, ToField } from "../../util/Scripting"; -import { KeyStore as KS, Key, KeyStore } from "../../../fields/Key"; +import { KeyStore } from "../../../fields/KeyStore"; import { Document } from "../../../fields/Document"; import { Field } from "../../../fields/Field"; import { Transform } from "../../util/Transform"; @@ -19,7 +19,7 @@ import Measure from "react-measure"; @observer export class CollectionSchemaView extends CollectionViewBase { - public static LayoutString() { return CollectionViewBase.LayoutString("CollectionSchemaView"); } + public static LayoutString() { return FieldView.LayoutString(CollectionSchemaView); } @observable selectedIndex = 0; @@ -106,8 +106,8 @@ export class CollectionSchemaView extends CollectionViewBase { render() { const { Document: Document, fieldKey: fieldKey } = this.props; const children = Document.GetList<Document>(fieldKey, []); - const columns = Document.GetList(KS.ColumnsKey, - [KS.Title, KS.Data, KS.Author]) + const columns = Document.GetList(KeyStore.ColumnsKey, + [KeyStore.Title, KeyStore.Data, KeyStore.Author]) let content; var me = this; if (this.selectedIndex != -1) { diff --git a/src/client/views/collections/CollectionViewBase.tsx b/src/client/views/collections/CollectionViewBase.tsx index 1e20da8d2..0a90bd0f2 100644 --- a/src/client/views/collections/CollectionViewBase.tsx +++ b/src/client/views/collections/CollectionViewBase.tsx @@ -2,7 +2,7 @@ import { action, computed } from "mobx"; import { observer } from "mobx-react"; import { Document } from "../../../fields/Document"; import { Opt } from "../../../fields/Field"; -import { Key, KeyStore } from "../../../fields/Key"; +import { Key } from "../../../fields/Key"; import { ListField } from "../../../fields/ListField"; import { SelectionManager } from "../../util/SelectionManager"; import { ContextMenu } from "../ContextMenu"; diff --git a/src/client/views/nodes/CollectionFreeFormDocumentView.tsx b/src/client/views/nodes/CollectionFreeFormDocumentView.tsx index 2eb0c5857..bb85f85a3 100644 --- a/src/client/views/nodes/CollectionFreeFormDocumentView.tsx +++ b/src/client/views/nodes/CollectionFreeFormDocumentView.tsx @@ -1,6 +1,6 @@ import { action, computed } from "mobx"; import { observer } from "mobx-react"; -import { Key, KeyStore } from "../../../fields/Key"; +import { KeyStore } from "../../../fields/KeyStore"; import { NumberField } from "../../../fields/NumberField"; import { DragManager } from "../../util/DragManager"; import { SelectionManager } from "../../util/SelectionManager"; @@ -10,6 +10,7 @@ import { ContextMenu } from "../ContextMenu"; import "./DocumentView.scss"; import React = require("react"); import { DocumentView, DocumentViewProps } from "./DocumentView"; +import { Utils } from "../../../Utils"; import { Transform } from "../../util/Transform"; diff --git a/src/client/views/nodes/DocumentView.tsx b/src/client/views/nodes/DocumentView.tsx index f8770f020..ee1a835f8 100644 --- a/src/client/views/nodes/DocumentView.tsx +++ b/src/client/views/nodes/DocumentView.tsx @@ -1,8 +1,9 @@ import { action, computed } from "mobx"; import { observer } from "mobx-react"; import { Document } from "../../../fields/Document"; -import { Opt, FieldWaiting } from "../../../fields/Field"; -import { Key, KeyStore } from "../../../fields/Key"; +import { Opt, FieldWaiting, Field } from "../../../fields/Field"; +import { Key } from "../../../fields/Key"; +import { KeyStore } from "../../../fields/KeyStore"; import { ListField } from "../../../fields/ListField"; import { Utils } from "../../../Utils"; import { CollectionDockingView } from "../collections/CollectionDockingView"; @@ -31,6 +32,47 @@ export interface DocumentViewProps { //tfs: This shouldn't be necessary I don't think Scaling: number; } +export interface JsxArgs extends DocumentViewProps { + Keys: { [name: string]: Key } + Fields: { [name: string]: Field } +} + +/* +This function is pretty much a hack that lets us fill out the fields in JsxArgs with something that +jsx-to-string can recover the jsx from +Example usage of this function: + public static LayoutString() { + let args = FakeJsxArgs(["Data"]); + return jsxToString( + <CollectionFreeFormView + doc={args.Document} + fieldKey={args.Keys.Data} + DocumentViewForField={args.DocumentView} />, + { useFunctionCode: true, functionNameOnly: true } + ) + } +*/ +export function FakeJsxArgs(keys: string[], fields: string[] = []): JsxArgs { + let Keys: { [name: string]: any } = {} + let Fields: { [name: string]: any } = {} + for (const key of keys) { + let fn = () => { } + Object.defineProperty(fn, "name", { value: key + "Key" }) + Keys[key] = fn; + } + for (const field of fields) { + let fn = () => { } + Object.defineProperty(fn, "name", { value: field }) + Fields[field] = fn; + } + let args: JsxArgs = { + Document: function Document() { }, + DocumentView: function DocumentView() { }, + Keys, + Fields + } as any; + return args; +} @observer export class DocumentView extends React.Component<DocumentViewProps> { @@ -218,6 +260,10 @@ export class DocumentView extends React.Component<DocumentViewProps> { } render() { + let lkeys = this.props.Document.GetT(KeyStore.LayoutKeys, ListField); + if (!lkeys || lkeys === "<Waiting>") { + return <p>Error loading layout keys</p>; + } let bindings = { ...this.props } as any; bindings.isSelected = this.isSelected; bindings.select = this.select; diff --git a/src/client/views/nodes/FieldView.tsx b/src/client/views/nodes/FieldView.tsx index 08de53e1c..918acff4c 100644 --- a/src/client/views/nodes/FieldView.tsx +++ b/src/client/views/nodes/FieldView.tsx @@ -25,7 +25,7 @@ export interface FieldViewProps { @observer export class FieldView extends React.Component<FieldViewProps> { - public static LayoutString(fieldType: string) { return `<${fieldType} doc={Document} DocumentViewForField={DocumentView} fieldKey={DataKey} isSelected={isSelected} isTopMost={isTopMost} />`; } + public static LayoutString(fieldType: { name: string }) { return `<${fieldType.name} doc={Document} DocumentViewForField={DocumentView} fieldKey={DataKey} isSelected={isSelected} isTopMost={isTopMost} />`; } @computed get field(): FieldValue<Field> { const { doc, fieldKey } = this.props; diff --git a/src/client/views/nodes/FormattedTextBox.tsx b/src/client/views/nodes/FormattedTextBox.tsx index 2e3d396c1..b17650d06 100644 --- a/src/client/views/nodes/FormattedTextBox.tsx +++ b/src/client/views/nodes/FormattedTextBox.tsx @@ -33,7 +33,7 @@ import { observer } from "mobx-react"; //] export class FormattedTextBox extends React.Component<FieldViewProps> { - public static LayoutString() { return FieldView.LayoutString("FormattedTextBox"); } + public static LayoutString() { return FieldView.LayoutString(FormattedTextBox) } private _ref: React.RefObject<HTMLDivElement>; private _editorView: Opt<EditorView>; private _reactionDisposer: Opt<IReactionDisposer>; diff --git a/src/client/views/nodes/ImageBox.tsx b/src/client/views/nodes/ImageBox.tsx index e1fa26e2f..b5ce8b28c 100644 --- a/src/client/views/nodes/ImageBox.tsx +++ b/src/client/views/nodes/ImageBox.tsx @@ -1,21 +1,19 @@ import Lightbox from 'react-image-lightbox'; import 'react-image-lightbox/style.css'; // This only needs to be imported once in your app -import { SelectionManager } from "../../util/SelectionManager"; import "./ImageBox.scss"; import React = require("react") import { ImageField } from '../../../fields/ImageField'; import { FieldViewProps, FieldView } from './FieldView'; -import { CollectionFreeFormDocumentView } from './CollectionFreeFormDocumentView'; import { FieldWaiting } from '../../../fields/Field'; import { observer } from "mobx-react" -import { observable, action, spy } from 'mobx'; -import { KeyStore } from '../../../fields/Key'; +import { observable, action } from 'mobx'; +import { KeyStore } from '../../../fields/KeyStore'; @observer export class ImageBox extends React.Component<FieldViewProps> { - public static LayoutString() { return FieldView.LayoutString("ImageBox"); } + public static LayoutString() { return FieldView.LayoutString(ImageBox) } private _ref: React.RefObject<HTMLDivElement>; private _downX: number = 0; private _downY: number = 0; |
