diff options
Diffstat (limited to 'src/views/nodes/DocumentView.tsx')
-rw-r--r-- | src/views/nodes/DocumentView.tsx | 166 |
1 files changed, 104 insertions, 62 deletions
diff --git a/src/views/nodes/DocumentView.tsx b/src/views/nodes/DocumentView.tsx index 772c272bd..33a126a7b 100644 --- a/src/views/nodes/DocumentView.tsx +++ b/src/views/nodes/DocumentView.tsx @@ -1,48 +1,49 @@ import { observer } from "mobx-react"; import React = require("react"); -import { computed, observable } from "mobx"; +import { computed, observable, action } from "mobx"; import { KeyStore, Key } from "../../fields/Key"; import { NumberField } from "../../fields/NumberField"; import { TextField } from "../../fields/TextField"; import { DocumentViewModel } from "../../viewmodels/DocumentViewModel"; import { ListField } from "../../fields/ListField"; import { FieldTextBox } from "../nodes/FieldTextBox" -import { FreeFormCanvas } from "../freeformcanvas/FreeFormCanvas" +import { Document } from "../../fields/Document"; import { CollectionFreeFormView } from "../freeformcanvas/CollectionFreeFormView" import "./NodeView.scss" import { SelectionManager } from "../../util/SelectionManager"; import { DocumentDecorations } from "../../DocumentDecorations"; -import { SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS } from "constants"; -import { DragManager } from "../../util/DragManager"; -import { Document } from "../../fields/Document"; +import { ContextMenu } from "../ContextMenu"; +import { Opt } from "../../fields/Field"; const JsxParser = require('react-jsx-parser').default;//TODO Why does this need to be imported like this? interface IProps { - dvm: Document; + Document: Document; + ContainingCollectionView: Opt<object>; + ContainingDocumentView: Opt<DocumentView> } @observer -class DocumentContents extends React.Component<IProps & {isSelected: () => boolean}> { +class DocumentContents extends React.Component<IProps> { @computed get layout(): string { - return this.props.dvm.GetFieldValue(KeyStore.Layout, TextField, String("<p>Error loading layout data</p>")); + return this.props.Document.GetFieldValue(KeyStore.Layout, TextField, String("<p>Error loading layout data</p>")); } @computed get layoutKeys(): Key[] { - return this.props.dvm.GetFieldValue(KeyStore.LayoutKeys, ListField, new Array<Key>()); + return this.props.Document.GetFieldValue(KeyStore.LayoutKeys, ListField, new Array<Key>()); } @computed get layoutFields(): Key[] { - return this.props.dvm.GetFieldValue(KeyStore.LayoutFields, ListField, new Array<Key>()); + return this.props.Document.GetFieldValue(KeyStore.LayoutFields, ListField, new Array<Key>()); } render() { - let doc = this.props.dvm; + let doc = this.props.Document; let bindings: any = { doc: doc, - isSelected: this.props.isSelected + // isSelected: this.props.isSelected }; for (const key of this.layoutKeys) { bindings[key.Name + "Key"] = key; @@ -54,7 +55,7 @@ class DocumentContents extends React.Component<IProps & {isSelected: () => boole } } return <JsxParser - components={{ FieldTextBox, FreeFormCanvas, CollectionFreeFormView }} + components={{ FieldTextBox, CollectionFreeFormView }} bindings={bindings} jsx={this.layout} showWarnings={true} @@ -69,6 +70,11 @@ class DocumentContents extends React.Component<IProps & {isSelected: () => boole @observer export class DocumentView extends React.Component<IProps> { private _mainCont = React.createRef<HTMLDivElement>(); + private _contextMenuCanOpen = false; + private _downX:number = 0; + private _downY:number = 0; + private _lastX:number = 0; + private _lastY:number = 0; get screenRect(): ClientRect | DOMRect { if (this._mainCont.current) { @@ -79,20 +85,20 @@ export class DocumentView extends React.Component<IProps> { @computed get x(): number { - return this.props.dvm.GetFieldValue(KeyStore.X, NumberField, Number(0)); + return this.props.Document.GetFieldValue(KeyStore.X, NumberField, Number(0)); } @computed get y(): number { - return this.props.dvm.GetFieldValue(KeyStore.Y, NumberField, Number(0)); + return this.props.Document.GetFieldValue(KeyStore.Y, NumberField, Number(0)); } set x(x: number) { - this.props.dvm.SetFieldValue(KeyStore.X, x, NumberField) + this.props.Document.SetFieldValue(KeyStore.X, x, NumberField) } set y(y: number) { - this.props.dvm.SetFieldValue(KeyStore.Y, y, NumberField) + this.props.Document.SetFieldValue(KeyStore.Y, y, NumberField) } @computed @@ -102,33 +108,22 @@ export class DocumentView extends React.Component<IProps> { @computed get width(): number { - return this.props.dvm.GetFieldValue(KeyStore.Width, NumberField, Number(0)); + return this.props.Document.GetFieldValue(KeyStore.Width, NumberField, Number(0)); } set width(w: number) { - this.props.dvm.SetFieldValue(KeyStore.Width, w, NumberField) + this.props.Document.SetFieldValue(KeyStore.Width, w, NumberField) } @computed get height(): number { - return this.props.dvm.GetFieldValue(KeyStore.Height, NumberField, Number(0)); + return this.props.Document.GetFieldValue(KeyStore.Height, NumberField, Number(0)); } set height(h: number) { - this.props.dvm.SetFieldValue(KeyStore.Height, h, NumberField) - } - - @computed - get selected(): boolean { - return SelectionManager.IsSelected(this) - } - - isSelected = (): boolean => { - return this.selected + this.props.Document.SetFieldValue(KeyStore.Height, h, NumberField) } - private _isPointerDown = false; - componentDidMount() { // if(this._mainCont.current) { // DragManager.MakeDraggable(this._mainCont.current, { @@ -141,40 +136,59 @@ export class DocumentView extends React.Component<IProps> { // } } + @computed + get active() : boolean { + return SelectionManager.IsSelected(this) || (this.props.ContainingCollectionView instanceof CollectionFreeFormView && this.props.ContainingCollectionView.active); + } + onPointerDown = (e: React.PointerEvent): void => { - // return; - e.stopPropagation(); - if (e.button === 2) { - this._isPointerDown = true; - document.removeEventListener("pointermove", this.onPointerMove); - document.addEventListener("pointermove", this.onPointerMove); - document.removeEventListener("pointerup", this.onPointerUp); - document.addEventListener("pointerup", this.onPointerUp); - } else { - SelectionManager.SelectDoc(this, e.ctrlKey) - } + this._downX = e.pageX; + this._downY = e.pageY; + this._lastX = e.pageX; + this._lastY = e.pageY; + this._contextMenuCanOpen = e.button == 2; + document.removeEventListener("pointermove", this.onPointerMove); + document.addEventListener("pointermove", this.onPointerMove); + document.removeEventListener("pointerup", this.onPointerUp); + document.addEventListener("pointerup", this.onPointerUp); } onPointerUp = (e: PointerEvent): void => { - e.stopPropagation(); - if (e.button === 2) { + document.removeEventListener("pointermove", this.onPointerMove); + document.removeEventListener("pointerup", this.onPointerUp); + if (!e.cancelBubble) { + e.stopPropagation(); e.preventDefault(); - this._isPointerDown = false; - document.removeEventListener("pointermove", this.onPointerMove); - document.removeEventListener("pointerup", this.onPointerUp); - DocumentDecorations.Instance.opacity = 1 + DocumentDecorations.Instance.opacity = 1; + if (this._downX == e.pageX && this._downY == e.pageY) { + SelectionManager.SelectDoc(this, e.ctrlKey) + } } } onPointerMove = (e: PointerEvent): void => { - e.stopPropagation(); - e.preventDefault(); - if (!this._isPointerDown) { - return; + if (this.active && !e.cancelBubble) { + e.stopPropagation(); + e.preventDefault(); + this._contextMenuCanOpen = false + let me = this; + var dx = e.pageX - this._lastX; + var dy = e.pageY - this._lastY; + this._lastX = e.pageX; + this._lastY = e.pageY; + let currScale:number = 1; + if (me.props.ContainingDocumentView != undefined) { + let pme = me.props.ContainingDocumentView!.props.Document; + currScale = pme.GetFieldValue(KeyStore.Scale, NumberField, Number(0)); + if (me.props.ContainingDocumentView!.props.ContainingDocumentView != undefined) { + let pme = me.props.ContainingDocumentView!.props.ContainingDocumentView!.props.Document; + currScale *= pme.GetFieldValue(KeyStore.Scale, NumberField, Number(0)); + } + } + this.x += dx/currScale; + this.y += dy/currScale; + DocumentDecorations.Instance.opacity = 0; } - this.x += e.movementX; - this.y += e.movementY; - //DocumentDecorations.Instance.opacity = 0 } onDragStart = (e: React.DragEvent<HTMLDivElement>): void => { @@ -184,6 +198,36 @@ export class DocumentView extends React.Component<IProps> { } } + onClick = (e: React.MouseEvent): void => { } + + deleteClicked = (e: React.MouseEvent): void => { + if (this.props.ContainingCollectionView instanceof CollectionFreeFormView) { + this.props.ContainingCollectionView.removeDocument(this.props.Document) + } + } + + @action + onContextMenu = (e: React.MouseEvent): void => { + e.preventDefault() + + if (!this._contextMenuCanOpen) { + return; + } + + var topMost = this.props.ContainingCollectionView == undefined; + if (topMost) { + ContextMenu.Instance.clearItems() + } + else { + // DocumentViews should stop propogation of this event + e.stopPropagation(); + + ContextMenu.Instance.clearItems(); + ContextMenu.Instance.addItem({description: "Delete", event: this.deleteClicked}) + ContextMenu.Instance.displayMenu(e.pageX, e.pageY) + } + } + render() { return ( <div className="node" ref={this._mainCont} style={{ @@ -191,12 +235,10 @@ export class DocumentView extends React.Component<IProps> { width: this.width, height: this.height, }} - onContextMenu={ - (e) => { - e.preventDefault() - }} - onPointerDown={this.onPointerDown}> - <DocumentContents dvm={this.props.dvm} isSelected={this.isSelected} /> + onContextMenu={this.onContextMenu} + onPointerDown={this.onPointerDown} + onClick={this.onClick}> + <DocumentContents {...this.props} /> </div> ); } |