aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorNathan-SR <144961007+Nathan-SR@users.noreply.github.com>2024-07-15 01:38:38 -0400
committerNathan-SR <144961007+Nathan-SR@users.noreply.github.com>2024-07-15 01:38:38 -0400
commite0dbe3a59d2e1e61fda951c250ef8d43cc0ccd3d (patch)
tree5bbe51881b68f9277a08812b30e1c450ab851119 /src
parent5e619c3f2491ee78297ac00329bb9c0a11132e6e (diff)
layout options/preview progress
Diffstat (limited to 'src')
-rw-r--r--src/client/views/nodes/DataVizBox/DocCreatorMenu.scss14
-rw-r--r--src/client/views/nodes/DataVizBox/DocCreatorMenu.tsx250
2 files changed, 174 insertions, 90 deletions
diff --git a/src/client/views/nodes/DataVizBox/DocCreatorMenu.scss b/src/client/views/nodes/DataVizBox/DocCreatorMenu.scss
index 71ad9e105..e3530c0ef 100644
--- a/src/client/views/nodes/DataVizBox/DocCreatorMenu.scss
+++ b/src/client/views/nodes/DataVizBox/DocCreatorMenu.scss
@@ -271,12 +271,26 @@
}
.docCreatorMenu-layout-preview-window {
+ padding: 5px;
+ overflow: scroll;
aspect-ratio: 1 / 1;
+ display: grid;
width: 85%;
border: 1px solid whitesmoke;
border-radius: 5px;
background-color: rgb(34, 34, 37);
margin-top: 10px;
+ -ms-overflow-style: none;
+ scrollbar-width: none;
+
+ .docCreatorMenu-layout-preview-item {
+ display: flex;
+ justify-content: center;
+ align-items: center;
+ border-radius: 3px;
+ border: solid 1px lightblue;
+ }
}
}
+
diff --git a/src/client/views/nodes/DataVizBox/DocCreatorMenu.tsx b/src/client/views/nodes/DataVizBox/DocCreatorMenu.tsx
index a45234a79..c8b414c59 100644
--- a/src/client/views/nodes/DataVizBox/DocCreatorMenu.tsx
+++ b/src/client/views/nodes/DataVizBox/DocCreatorMenu.tsx
@@ -1,9 +1,9 @@
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
-import { IReactionDisposer, ObservableMap, action, makeObservable, observable, reaction, runInAction } from 'mobx';
+import { IReactionDisposer, ObservableMap, action, computed, makeObservable, observable, reaction, runInAction } from 'mobx';
import { observer } from 'mobx-react';
import * as React from 'react';
import { returnAll, returnFalse, setupMoveUpEvents } from '../../../../ClientUtils';
-import { Doc } from '../../../../fields/Doc';
+import { Doc, NumListCast } from '../../../../fields/Doc';
import { DocCast, ImageCast } from '../../../../fields/Types';
import { ImageField } from '../../../../fields/URLField';
import { emptyFunction } from '../../../../Utils';
@@ -16,6 +16,7 @@ import './DocCreatorMenu.scss';
import { Id } from '../../../../fields/FieldSymbols';
import { Colors } from 'browndash-components';
import { MakeTemplate } from '../../../util/DropConverter';
+import { threadId } from 'worker_threads';
export enum LayoutType {
Stacked = 'stacked',
@@ -37,7 +38,7 @@ export class DocCreatorMenu extends ObservableReactComponent<{}> {
@observable _templateRefToDoc?: ObservableMap<HTMLDivElement, Doc>;
@observable _selectedTemplate: Doc | undefined = undefined;
- @observable _selectedLayout: LayoutType | undefined = undefined;
+ @observable _layout: {type?: LayoutType, yMargin: number, xMargin: number, rows?:number, columns?: number} = {yMargin: 0, xMargin: 0};
@observable _layoutPreview: boolean = false;
@observable _pageX: number = 0;
@@ -62,6 +63,35 @@ export class DocCreatorMenu extends ObservableReactComponent<{}> {
@action setDataViz = (dataViz: DataVizBox) => { this._dataViz = dataViz };
@action setTemplateDocs = (docs: Doc[]) => {this._templateDocs = docs.map(doc => doc.annotationOn ? DocCast(doc.annotationOn):doc)};
+ @computed get docsToRender() {
+ return NumListCast(this._dataViz?.layoutDoc.dataViz_selectedRows);
+ }
+
+ @computed get rowsCount(){
+ switch (this._layout.type) {
+ case LayoutType.Row: case LayoutType.Stacked:
+ return 1;
+ case LayoutType.Column:
+ return this.docsToRender.length;
+ case LayoutType.Grid:
+ return this._layout.rows ?? 0;
+ default:
+ return 0;
+ }
+ }
+
+ @computed get columnsCount(){
+ switch (this._layout.type) {
+ case LayoutType.Row:
+ return this.docsToRender.length;
+ case LayoutType.Column: case LayoutType.Stacked:
+ return 1;
+ case LayoutType.Grid:
+ return this._layout.columns ?? 0;
+ default:
+ return 0;
+ }
+ }
@action
onPointerDown = (e: PointerEvent) => {
@@ -158,40 +188,50 @@ export class DocCreatorMenu extends ObservableReactComponent<{}> {
);
}
+ @action updateXMargin = (input: string) => { this._layout.xMargin = Number(input) };
+ @action updateYMargin = (input: string) => { this._layout.yMargin = Number(input) };
+ @action updateDimensions = (dimension: 'x' | 'y', input: string) => {
+ if (dimension === 'x') {
+ this._layout.rows = Number(input);
+ } else {
+ this._layout.columns = Number(input);
+ }
+ };
+
get layoutConfigOptions() {
- const optionInput = (title: string) => {
+ const optionInput = (title: string, func: Function) => {
return (
<div className='docCreatorMenu-option-container'>
<div className='docCreatorMenu-option-title config layout-config'>
{title}
</div>
- <input className='docCreatorMenu-input config layout-config'/>
+ <input onInput={(e) => func(e.currentTarget.value)} className='docCreatorMenu-input config layout-config'/>
</div>
);
}
- switch (this._selectedLayout) {
+ switch (this._layout.type) {
case LayoutType.Row: case LayoutType.Column:
return (
<div className='docCreatorMenu-configuration-bar'>
- {optionInput('Y Margin:')}
- {optionInput('X Margin:')}
+ {optionInput('Y Margin:', this.updateYMargin)}
+ {optionInput('X Margin:', this.updateXMargin)}
</div>
);
case LayoutType.Grid:
return (
<>
<div className='docCreatorMenu-configuration-bar'>
- {optionInput('Y Margin:')}
- {optionInput('X Margin:')}
+ {optionInput('Y Margin:', this.updateYMargin)}
+ {optionInput('X Margin:', this.updateXMargin)}
</div>
<div className='docCreatorMenu-configuration-bar no-gap'>
<div className='docCreatorMenu-option-title config dimensions'>
Dimensions:
</div>
- <input className='docCreatorMenu-input config dimensions left'/>
+ <input className='docCreatorMenu-input config dimensions left' onInput={(e) => {this.updateDimensions('x', e.currentTarget.value); this.forceUpdate()}}/>
<div className='docCreatorMenu-option-title spacer small'>x</div>
- <input className='docCreatorMenu-input config dimensions right'/>
+ <input className='docCreatorMenu-input config dimensions right' onInput={(e) => this.updateDimensions('y', e.currentTarget.value)}/>
</div>
</>
);
@@ -203,8 +243,38 @@ export class DocCreatorMenu extends ObservableReactComponent<{}> {
}
get layoutPreviewContents() {
+ const docWidth = Number(this._selectedTemplate?._width);
+ const docHeight = Number(this._selectedTemplate?._height);
+ const horizontalSpan: number = (docWidth + this._layout.xMargin) * this.columnsCount - this._layout.xMargin;
+ const verticalSpan: number = (docHeight + this._layout.yMargin) * this.rowsCount - this._layout.yMargin;
+ const largerSpan: number = horizontalSpan > verticalSpan ? horizontalSpan : verticalSpan;
+ const scaleDownFactor: number = largerSpan / 235;
+ const scaledWidth = docWidth / scaleDownFactor;
+ const scaledHeight = docHeight / scaleDownFactor;
+
+ console.log(this.rowsCount);
+ console.log(this.columnsCount)
+
return (
- <div className='docCreatorMenu-layout-preview-window'>
+ <div
+ className='docCreatorMenu-layout-preview-window'
+ style={{
+ gridTemplateColumns: `repeat(${this.columnsCount}, ${scaledWidth}px)`,
+ gridTemplateRows: `repeat(${this.rowsCount}, ${scaledHeight}px)`,
+ rowGap: `${this._layout.yMargin}px`,
+ columnGap: `${this._layout.xMargin}px`
+ }}>
+ {this.docsToRender.map(num =>
+ <div
+ className='docCreatorMenu-layout-preview-item'
+ style={{
+ width: scaledWidth,
+ height: scaledHeight,
+ }}
+ >
+ {num}
+ </div>
+ )}
</div>
);
@@ -220,7 +290,7 @@ export class DocCreatorMenu extends ObservableReactComponent<{}> {
setupMoveUpEvents(this, e, returnFalse, emptyFunction,
undoable(clickEv => {
clickEv.stopPropagation();
- runInAction(() => this._selectedLayout = option);
+ runInAction(() => this._layout.type = option);
}, 'open actions menu')
)
}>
@@ -248,7 +318,7 @@ export class DocCreatorMenu extends ObservableReactComponent<{}> {
<div className='docCreatorMenu-menu-container'>
<div className='docCreatorMenu-option-container layout'>
<div className='docCreatorMenu-dropdown-hoverable'>
- <div className="docCreatorMenu-option-title">{this._selectedLayout ? this._selectedLayout.toUpperCase() : 'Choose Layout'}</div>
+ <div className="docCreatorMenu-option-title">{this._layout.type ? this._layout.type.toUpperCase() : 'Choose Layout'}</div>
<div className="docCreatorMenu-dropdown-content">
{layoutOption(LayoutType.Stacked)}
{layoutOption(LayoutType.Grid)}
@@ -270,7 +340,7 @@ export class DocCreatorMenu extends ObservableReactComponent<{}> {
<FontAwesomeIcon icon={this._layoutPreview ? 'minus' : 'magnifying-glass'}/>
</button>
</div>
- {this._selectedLayout ? this.layoutConfigOptions: null}
+ {this._layout.type ? this.layoutConfigOptions: null}
{this._layoutPreview ? this.layoutPreviewContents : null}
{selectionBox(100, 30, 'Repeat:', undefined, repeatOptions.map(num => <option onPointerDown={e => this._templateInfo.repeat = num}>{`${num}x`}</option>))}
</div>
@@ -279,79 +349,61 @@ export class DocCreatorMenu extends ObservableReactComponent<{}> {
render() {
return (
- <div
- className="docCreatorMenu-cont"
- ref={r => this._ref = r}
- style={{
- display: '',
- left: this._pageX,
- top: this._pageY,
- width: this._shouldDisplay ? 300 : 0,
- height: this._shouldDisplay ? 400 : 0,
- background: SnappingManager.userBackgroundColor,
- color: SnappingManager.userColor,
- }}>
- {!this._shouldDisplay ? undefined :
- <>
- <div
- className='docCreatorMenu-menu'
- onPointerDown={e =>
- setupMoveUpEvents(
- this,
- e,
- (e) => {
- this._dragging = true;
- this._startPos = {x: 0, y: 0};
- this._startPos.x = e.pageX - (this._ref?.getBoundingClientRect().left ?? 0);
- this._startPos.y = e.pageY - (this._ref?.getBoundingClientRect().top ?? 0);
- return true;
- },
- emptyFunction,
- undoable(clickEv => {
- clickEv.stopPropagation();
- }, 'drag menu')
- )
- }
- onPointerMove={e => this.onPointerMove(e)}
- onPointerUp={() => this._dragging = false}
- >
- <button
- className='docCreatorMenu-menu-button'
- onPointerDown={e =>
- setupMoveUpEvents(
- this,
- e,
- returnFalse,
- emptyFunction,
- undoable(clickEv => {
- clickEv.stopPropagation();
- runInAction(() => this._menuContent = this._menuContent === 'templates' ? 'options' : 'templates');
- }, 'create docs')
- )
- }
- >
- <FontAwesomeIcon icon={this._menuContent === 'templates' ? 'bars' : 'table-cells'}/>
- </button>
- <button
- className='docCreatorMenu-menu-button right'
+ <div className='docCreatorMenu'>
+ {!this._shouldDisplay ? undefined :
+ <div
+ className="docCreatorMenu-cont"
+ ref={r => this._ref = r}
+ style={{
+ display: '',
+ left: this._pageX,
+ top: this._pageY,
+ width: 300,
+ height: 400,
+ background: SnappingManager.userBackgroundColor,
+ color: SnappingManager.userColor,
+ }}>
+ <div
+ className='docCreatorMenu-menu'
onPointerDown={e =>
setupMoveUpEvents(
this,
e,
- returnFalse,
+ (e) => {
+ this._dragging = true;
+ this._startPos = {x: 0, y: 0};
+ this._startPos.x = e.pageX - (this._ref?.getBoundingClientRect().left ?? 0);
+ this._startPos.y = e.pageY - (this._ref?.getBoundingClientRect().top ?? 0);
+ return true;
+ },
emptyFunction,
undoable(clickEv => {
clickEv.stopPropagation();
- if (!this._selectedTemplate) return;
- const templateInfo: DataVizTemplateInfo = {doc: this._selectedTemplate};
- this._dataViz?.createDocsFromTemplate(templateInfo);
- }, 'make docs')
+ }, 'drag menu')
)
- }>
- <FontAwesomeIcon icon={'plus'}/>
- </button>
- <button
- className='docCreatorMenu-menu-button close-menu'
+ }
+ onPointerMove={e => this.onPointerMove(e)}
+ onPointerUp={() => this._dragging = false}
+ >
+ <button
+ className='docCreatorMenu-menu-button'
+ onPointerDown={e =>
+ setupMoveUpEvents(
+ this,
+ e,
+ returnFalse,
+ emptyFunction,
+ undoable(clickEv => {
+ clickEv.stopPropagation();
+ runInAction(() => this._menuContent = this._menuContent === 'templates' ? 'options' : 'templates');
+ }, 'create docs')
+ )
+ }
+ >
+ <FontAwesomeIcon icon={this._menuContent === 'templates' ? 'bars' : 'table-cells'}/>
+ </button>
+ <button
+ className='docCreatorMenu-menu-button right'
onPointerDown={e =>
setupMoveUpEvents(
this,
@@ -360,17 +412,35 @@ export class DocCreatorMenu extends ObservableReactComponent<{}> {
emptyFunction,
undoable(clickEv => {
clickEv.stopPropagation();
- this.closeMenu();
- }, 'close menu')
+ if (!this._selectedTemplate) return;
+ const templateInfo: DataVizTemplateInfo = {doc: this._selectedTemplate};
+ this._dataViz?.createDocsFromTemplate(templateInfo);
+ }, 'make docs')
)
}>
- <FontAwesomeIcon icon={'minus'}/>
- </button>
- </div>
- <hr className='docCreatorMenu-menu-hr'/>
- {this._menuContent === 'templates' ? this.templatesPreviewContents : this.optionsMenuContents}
- </>
- }
+ <FontAwesomeIcon icon={'plus'}/>
+ </button>
+ <button
+ className='docCreatorMenu-menu-button close-menu'
+ onPointerDown={e =>
+ setupMoveUpEvents(
+ this,
+ e,
+ returnFalse,
+ emptyFunction,
+ undoable(clickEv => {
+ clickEv.stopPropagation();
+ this.closeMenu();
+ }, 'close menu')
+ )
+ }>
+ <FontAwesomeIcon icon={'minus'}/>
+ </button>
+ </div>
+ <hr className='docCreatorMenu-menu-hr'/>
+ {this._menuContent === 'templates' ? this.templatesPreviewContents : this.optionsMenuContents}
+ </div>
+ }
</div>
)
}