diff options
| author | bobzel <zzzman@gmail.com> | 2022-08-03 13:33:38 -0400 |
|---|---|---|
| committer | bobzel <zzzman@gmail.com> | 2022-08-03 13:33:38 -0400 |
| commit | 55bac585fa0b8d6c3f513ccecb22456d1d361040 (patch) | |
| tree | 3c4886b07ba775e656f264874d8552992f087abd /src/client/views/collections/CollectionNoteTakingView.tsx | |
| parent | 4ad4936393d11227934fdda2c18bea3446b20795 (diff) | |
fixes for dragging notes so that they highlight properly and go to the right place when embedded in freeform views.
Diffstat (limited to 'src/client/views/collections/CollectionNoteTakingView.tsx')
| -rw-r--r-- | src/client/views/collections/CollectionNoteTakingView.tsx | 91 |
1 files changed, 49 insertions, 42 deletions
diff --git a/src/client/views/collections/CollectionNoteTakingView.tsx b/src/client/views/collections/CollectionNoteTakingView.tsx index f442559fb..1854a4213 100644 --- a/src/client/views/collections/CollectionNoteTakingView.tsx +++ b/src/client/views/collections/CollectionNoteTakingView.tsx @@ -1,6 +1,6 @@ import React = require('react'); import { CursorProperty } from 'csstype'; -import { action, computed, IReactionDisposer, observable, reaction } from 'mobx'; +import { action, computed, IReactionDisposer, observable, reaction, runInAction } from 'mobx'; import { observer } from 'mobx-react'; import { DataSym, Doc, HeightSym, Opt, WidthSym } from '../../../fields/Doc'; import { Id } from '../../../fields/FieldSymbols'; @@ -21,10 +21,12 @@ import { ContextMenuProps } from '../ContextMenuItem'; import { LightboxView } from '../LightboxView'; import { CollectionFreeFormDocumentView } from '../nodes/CollectionFreeFormDocumentView'; import { DocFocusOptions, DocumentView, DocumentViewProps, ViewAdjustment } from '../nodes/DocumentView'; +import { FieldViewProps } from '../nodes/FieldView'; +import { FormattedTextBox } from '../nodes/formattedText/FormattedTextBox'; import { StyleProp } from '../StyleProvider'; import './CollectionNoteTakingView.scss'; import { CollectionNoteTakingViewColumn } from './CollectionNoteTakingViewColumn'; -import CollectionNoteTakingViewDivider from './CollectionNoteTakingViewDivider'; +import { CollectionNoteTakingViewDivider } from './CollectionNoteTakingViewDivider'; import { CollectionSubView } from './CollectionSubView'; const _global = (window /* browser */ || global) /* node */ as any; @@ -40,7 +42,6 @@ export type collectionNoteTakingViewProps = { @observer export class CollectionNoteTakingView extends CollectionSubView<Partial<collectionNoteTakingViewProps>>() { - _pivotFieldDisposer?: IReactionDisposer; _autoHeightDisposer?: IReactionDisposer; _masonryGridRef: HTMLDivElement | null = null; _draggerRef = React.createRef<HTMLDivElement>(); @@ -54,10 +55,10 @@ export class CollectionNoteTakingView extends CollectionSubView<Partial<collecti return this.props.chromeHidden || BoolCast(this.layoutDoc.chromeHidden); } @computed get columnHeaders() { - return Cast(this.layoutDoc._columnHeaders, listSpec(SchemaHeaderField), null); + return Cast(this.dataDoc.columnHeaders, listSpec(SchemaHeaderField), null); } - @computed get pivotField() { - return 'Col'; + @computed get notetakingCategoryField() { + return 'noteTakingCategory'; } @computed get filteredChildren() { return this.childLayoutPairs.filter(pair => pair.layout instanceof Doc && !pair.layout.hidden).map(pair => pair.layout); @@ -90,7 +91,7 @@ export class CollectionNoteTakingView extends CollectionSubView<Partial<collecti constructor(props: any) { super(props); if (this.columnHeaders === undefined) { - this.layoutDoc._columnHeaders = new List<SchemaHeaderField>([new SchemaHeaderField('New Column')]); + this.dataDoc.columnHeaders = new List<SchemaHeaderField>([new SchemaHeaderField('New Column')]); this.columnStartXCoords = [0]; // add all of the docs that have not been added to a column to this new column } else { @@ -126,18 +127,16 @@ export class CollectionNoteTakingView extends CollectionSubView<Partial<collecti // filter out the currently dragged docs from the child docs, since we will insert them later if (rowCol.length && DragManager.docsBeingDragged.length) { const docIdsToRemove = new Set(); - DragManager.docsBeingDragged.forEach(d => { - docIdsToRemove.add(d[Id]); - }); + DragManager.docsBeingDragged.forEach(d => docIdsToRemove.add(d[Id])); docs = docs.filter(d => !docIdsToRemove.has(d[Id])); } // this will sort the docs into the correct columns (minus the ones you're currently dragging) docs.map(d => { - if (!d[this.pivotField]) { - d[this.pivotField] = columnHeaders.length > 0 ? columnHeaders[0].heading : `New Column`; + if (!d[this.notetakingCategoryField]) { + d[this.notetakingCategoryField] = columnHeaders.length > 0 ? columnHeaders[0].heading : `New Column`; } - const sectionValue = d[this.pivotField] as object; + const sectionValue = d[this.notetakingCategoryField] as object; // look for if header exists already const existingHeader = columnHeaders.find(sh => sh.heading === sectionValue.toString()); @@ -156,14 +155,15 @@ export class CollectionNoteTakingView extends CollectionSubView<Partial<collecti return sections; } + removeDocDragHighlight = () => { + setTimeout( + action(() => (this.docsDraggedRowCol.length = 0)), + 100 + ); + }; componentDidMount() { super.componentDidMount?.(); - // reset section headers when a new filter is inputted - this._pivotFieldDisposer = reaction( - () => this.pivotField, - () => (this.layoutDoc._columnHeaders = new List()) - ); - + document.addEventListener('pointerup', this.removeDocDragHighlight, true); this._autoHeightDisposer = reaction( () => this.layoutDoc._autoHeight, autoHeight => autoHeight && this.props.setHeight?.(Math.min(NumCast(this.layoutDoc._maxHeight, Number.MAX_SAFE_INTEGER), this.headerMargin + Math.max(...this.refList.map(r => Number(getComputedStyle(r).height.replace('px', '')))))) @@ -171,8 +171,8 @@ export class CollectionNoteTakingView extends CollectionSubView<Partial<collecti } componentWillUnmount() { + document.removeEventListener('pointerup', this.removeDocDragHighlight, true); super.componentWillUnmount(); - this._pivotFieldDisposer?.(); this._autoHeightDisposer?.(); } @@ -227,6 +227,9 @@ export class CollectionNoteTakingView extends CollectionSubView<Partial<collecti }; styleProvider = (doc: Doc | undefined, props: Opt<DocumentViewProps>, property: string) => { + if (property === StyleProp.BoxShadow && doc && DragManager.docsBeingDragged.includes(doc)) { + return `#9c9396 ${StrCast(doc?.boxShadow, '10px 10px 0.9vw')}`; + } if (property === StyleProp.Opacity && doc) { if (this.props.childOpacity) { return this.props.childOpacity(); @@ -258,9 +261,9 @@ export class CollectionNoteTakingView extends CollectionSubView<Partial<collecti docViewPath={this.props.docViewPath} fitWidth={this.props.childFitWidth} isContentActive={emptyFunction} - originalBackgroundColor={StrCast(doc.backgroundColor)} + onKey={this.onKeyDown} //TODO: change this from a prop to a parameter passed into a function - isNoteTakingView={true} + dontHideOnDrag={true} isDocumentActive={this.isContentActive} LayoutTemplate={this.props.childLayoutTemplate} LayoutTemplateString={this.props.childLayoutString} @@ -307,7 +310,7 @@ export class CollectionNoteTakingView extends CollectionSubView<Partial<collecti // how to get the width of a document. Currently returns the width of the column (minus margins) // if a note doc. Otherwise, returns the normal width (for graphs, images, etc...) getDocWidth(d: Doc) { - const heading = d[this.pivotField] as object; + const heading = d[this.notetakingCategoryField] as object; const castedSectionValue = heading.toString(); const existingHeader = this.columnHeaders.find(sh => sh.heading === castedSectionValue); const colStartXCoords = this.columnStartXCoords; @@ -364,20 +367,14 @@ export class CollectionNoteTakingView extends CollectionSubView<Partial<collecti if (DragManager.docsBeingDragged.length && this.childDocList) { // get the current docs for the column based on the mouse's x coordinate // will use again later, which is why we're saving as local - const xCoord = e.clientX - 2 * this.gridGap; + const xCoord = this.props.ScreenToLocalTransform().transformPoint(e.clientX, e.clientY)[0] - 2 * this.gridGap; const colDocs = this.getDocsFromXCoord(xCoord); // get the index for where you need to insert the doc you are currently dragging - const clientY = e.clientY; + const clientY = this.props.ScreenToLocalTransform().transformPoint(e.clientX, e.clientY)[1]; let dropInd = -1; - // unsure whether we still want this dropAfter field - // let dropAfter = 0; - // manually set to 140, because not sure how to get exact value - let pos0 = 140; + let pos0 = (this.refList.lastElement() as HTMLDivElement).children[0].getBoundingClientRect().height + this.yMargin * 2; colDocs.forEach((doc, i) => { - const noteTakingDocTransform = () => this.getDocTransform(doc); - let pos1 = noteTakingDocTransform() - .inverse() - .transformPoint(0, this.getDocHeight(doc) + 2 * this.gridGap)[1]; + let pos1 = this.getDocHeight(doc) + 2 * this.gridGap; pos1 += pos0; // updating drop position based on y coordinates const yCoordInBetween = clientY > pos0 && (clientY < pos1 || i == colDocs.length - 1); @@ -393,10 +390,10 @@ export class CollectionNoteTakingView extends CollectionSubView<Partial<collecti // we alter the pivot fields of the docs in case they are moved to a new column. const colIndex = this.getColumnFromXCoord(xCoord); const colHeader = StrCast(this.columnHeaders[colIndex].heading); - DragManager.docsBeingDragged.forEach(d => (d[this.pivotField] = colHeader)); + DragManager.docsBeingDragged.forEach(d => (d[this.notetakingCategoryField] = colHeader)); // used to notify sections to re-render - // console.log([dropInd, this.getColumnFromXCoord(xCoord)]) - this.docsDraggedRowCol = [dropInd, this.getColumnFromXCoord(xCoord)]; + this.docsDraggedRowCol.length = 0; + this.docsDraggedRowCol.push(dropInd, this.getColumnFromXCoord(xCoord)); } }; @@ -425,7 +422,7 @@ export class CollectionNoteTakingView extends CollectionSubView<Partial<collecti if (docs) { docs.map(d => { if (d instanceof Promise) return; - const sectionValue = d[this.pivotField] as object; + const sectionValue = d[this.notetakingCategoryField] as object; if (sectionValue.toString() == colHeader) { docsMatchingHeader.push(d); } @@ -436,11 +433,22 @@ export class CollectionNoteTakingView extends CollectionSubView<Partial<collecti @undoBatch @action + onKeyDown = (e: React.KeyboardEvent, fieldProps: FieldViewProps) => { + const docView = fieldProps.DocumentView?.(); + if (docView && (e.ctrlKey || docView.rootDoc._singleLine) && ['Enter'].includes(e.key)) { + e.stopPropagation?.(); + const newDoc = Doc.MakeCopy(docView.rootDoc, true); + Doc.GetProto(newDoc).text = undefined; + FormattedTextBox.SelectOnLoad = newDoc[Id]; + return this.addDocument?.(newDoc); + } + }; + + @undoBatch + @action onInternalDrop = (e: Event, de: DragManager.DropEvent) => { if (de.complete.docDragData) { if (super.onInternalDrop(e, de)) { - DragManager.docsBeingDragged = []; - // this.docsDraggedRowCol = [] // filter out the currently dragged docs from the child docs, since we will insert them later const rowCol = this.docsDraggedRowCol; const droppedDocs = this.childDocs.slice().filter((d: Doc, ind: number) => ind >= this.childDocs.length); // if the drop operation adds something to the end of the list, then use that as the new document (may be different than what was dropped e.g., in the case of a button which is dropped but which creates say, a note). @@ -456,10 +464,9 @@ export class CollectionNoteTakingView extends CollectionSubView<Partial<collecti if (rowCol[0] <= 0) { docs.splice(0, 0, ...newDocs); } else { - const colDocs = this.getDocsFromXCoord(de.x); + const colDocs = this.getDocsFromXCoord(this.props.ScreenToLocalTransform().transformPoint(de.x, de.y)[0]); const previousDoc = colDocs[rowCol[0] - 1]; const previousDocIndex = docs.indexOf(previousDoc); - console.log(`docs: ${previousDocIndex}`); docs.splice(previousDocIndex + 1, 0, ...newDocs); } } @@ -561,7 +568,7 @@ export class CollectionNoteTakingView extends CollectionSubView<Partial<collecti renderChildren={this.children} numGroupColumns={this.numGroupColumns} gridGap={this.gridGap} - pivotField={this.pivotField} + pivotField={this.notetakingCategoryField} columnStartXCoords={this.columnStartXCoords} maxColWidth={this.maxColWdith} PanelWidth={this.PanelWidth} |
