diff --git a/src/Components/Editor/ContainerOperations.ts b/src/Components/Editor/ContainerOperations.ts index cbc0a9c..ec5a28a 100644 --- a/src/Components/Editor/ContainerOperations.ts +++ b/src/Components/Editor/ContainerOperations.ts @@ -55,9 +55,7 @@ export function DeleteContainer( throw new Error(`[DeleteContainer] Tried to delete a container that is not present in the main container: ${containerId}`); } - if (container === mainContainerClone || - container.parent === undefined || - container.parent === null) { + if (container === mainContainerClone) { // TODO: Implement alert throw new Error('[DeleteContainer] Tried to delete the main container! Deleting the main container is not allowed!'); } @@ -66,25 +64,18 @@ export function DeleteContainer( throw new Error('[DeleteContainer] Container model was not found among children of the main container!'); } - const index = container.parent.children.indexOf(container); - if (index > -1) { - container.parent.children.splice(index, 1); - } else { - throw new Error('[DeleteContainer] Could not find container among parent\'s children'); + if (container.parent != null) { + const index = container.parent.children.indexOf(container); + if (index > -1) { + container.parent.children.splice(index, 1); + } } - // Select the previous container - // or select the one above - const SelectedContainer = findContainerById(mainContainerClone, current.SelectedContainerId) ?? - container.parent.children.at(index - 1) ?? - container.parent; - const SelectedContainerId = SelectedContainer.properties.id; - setHistory(history.concat([{ LastAction: `Delete container ${containerId}`, MainContainer: mainContainerClone, - SelectedContainer, - SelectedContainerId, + SelectedContainer: null, + SelectedContainerId: '', TypeCounters: Object.assign({}, current.TypeCounters) }])); setHistoryCurrentStep(history.length); @@ -191,7 +182,6 @@ export function AddContainer( width: properties?.Width, height: parentClone.properties.height, isRigidBody: false, - XPositionReference: properties.XPositionReference, ...properties.Style }, [], diff --git a/src/Components/Editor/Save.ts b/src/Components/Editor/Save.ts index 3aa201a..91cee2f 100644 --- a/src/Components/Editor/Save.ts +++ b/src/Components/Editor/Save.ts @@ -1,4 +1,4 @@ -import { HistoryState } from '../../Interfaces/HistoryState'; +import { HistoryState } from "../../Interfaces/HistoryState"; import { Configuration } from '../../Interfaces/Configuration'; import { getCircularReplacer } from '../../utils/saveload'; import { ID } from '../SVG/SVG'; diff --git a/src/Components/ElementsSidebar/ElementsSidebar.tsx b/src/Components/ElementsSidebar/ElementsSidebar.tsx index e9d5e59..c0a89c6 100644 --- a/src/Components/ElementsSidebar/ElementsSidebar.tsx +++ b/src/Components/ElementsSidebar/ElementsSidebar.tsx @@ -9,6 +9,7 @@ import { MenuItem } from '../Menu/MenuItem'; import { handleDragLeave, handleDragOver, handleLeftClick, handleOnDrop, handleRightClick } from './MouseEventHandlers'; import { Point } from '../../Interfaces/Point'; + interface IElementsSidebarProps { MainContainer: IContainerModel isOpen: boolean @@ -107,7 +108,7 @@ export const ElementsSidebar: React.FC = (props: IElement onLeftClick ); }; - }); + }, []); // Render let isOpenClasses = '-right-64'; diff --git a/src/Components/SVG/Elements/Container.tsx b/src/Components/SVG/Elements/Container.tsx index 25a45c9..02dea6f 100644 --- a/src/Components/SVG/Elements/Container.tsx +++ b/src/Components/SVG/Elements/Container.tsx @@ -1,5 +1,4 @@ import * as React from 'react'; -import { XPositionReference } from '../../../Enums/XPositionReference'; import { IContainerModel } from '../../../Interfaces/ContainerModel'; import { getDepth } from '../../../utils/itertools'; import { Dimension } from './Dimension'; @@ -18,14 +17,7 @@ export const Container: React.FC = (props: IContainerProps) => const containersElements = props.model.children.map(child => ); const xText = Number(props.model.properties.width) / 2; const yText = Number(props.model.properties.height) / 2; - - const [transformedX, transformedY] = transformPosition( - Number(props.model.properties.x), - Number(props.model.properties.y), - Number(props.model.properties.width), - props.model.properties.XPositionReference - ); - const transform = `translate(${transformedX}, ${transformedY})`; + const transform = `translate(${Number(props.model.properties.x)}, ${Number(props.model.properties.y)})`; // g style const defaultStyle: React.CSSProperties = { @@ -62,8 +54,7 @@ export const Container: React.FC = (props: IContainerProps) => id={id} xStart={xStart} xEnd={xEnd} - yStart={y} - yEnd={y} + y={y} strokeWidth={strokeWidth} text={text} /> @@ -83,13 +74,3 @@ export const Container: React.FC = (props: IContainerProps) => ); }; - -function transformPosition(x: number, y: number, width: number, xPositionReference = XPositionReference.Left): [number, number] { - let transformedX = x; - if (xPositionReference === XPositionReference.Center) { - transformedX -= width / 2; - } else if (xPositionReference === XPositionReference.Right) { - transformedX -= width; - } - return [transformedX, y]; -} diff --git a/src/Components/SVG/Elements/Dimension.tsx b/src/Components/SVG/Elements/Dimension.tsx index 08f0a22..ec51873 100644 --- a/src/Components/SVG/Elements/Dimension.tsx +++ b/src/Components/SVG/Elements/Dimension.tsx @@ -3,80 +3,45 @@ import * as React from 'react'; interface IDimensionProps { id: string xStart: number - yStart: number xEnd: number - yEnd: number + y: number text: string strokeWidth: number } -/** - * 2D Parametric function. Returns a new coordinate from the origin coordinate - * See for more details https://en.wikipedia.org/wiki/Parametric_equation. - * TL;DR a parametric function is a function with a parameter - * @param x0 Origin coordinate - * @param t The parameter - * @param vx Transform vector - * @returns Returns a new coordinate from the origin coordinate - */ -const applyParametric = (x0: number, t: number, vx: number): number => x0 + t * vx; - export const Dimension: React.FC = (props: IDimensionProps) => { const style: React.CSSProperties = { stroke: 'black' }; - - /// We need to find the points of the notches - // Get the vector of the line - const [deltaX, deltaY] = [(props.xEnd - props.xStart), (props.yEnd - props.yStart)]; - - // Get the unit vector - const norm = Math.sqrt(deltaX * deltaX + deltaY * deltaY); - const [unitX, unitY] = [deltaX / norm, deltaY / norm]; - - // Get the perpandicular vector - const [perpVecX, perpVecY] = [unitY, -unitX]; - - // Use the parametric function to get the coordinates (x = x0 + t * v.x) - const startTopX = applyParametric(props.xStart, 4, perpVecX); - const startTopY = applyParametric(props.yStart, 4, perpVecY); - const startBottomX = applyParametric(props.xStart, -4, perpVecX); - const startBottomY = applyParametric(props.yStart, -4, perpVecY); - - const endTopX = applyParametric(props.xEnd, 4, perpVecX); - const endTopY = applyParametric(props.yEnd, 4, perpVecY); - const endBottomX = applyParametric(props.xEnd, -4, perpVecX); - const endBottomY = applyParametric(props.yEnd, -4, perpVecY); - return ( {props.text} diff --git a/src/Components/SVG/Elements/DimensionLayer.tsx b/src/Components/SVG/Elements/DimensionLayer.tsx new file mode 100644 index 0000000..85f1a43 --- /dev/null +++ b/src/Components/SVG/Elements/DimensionLayer.tsx @@ -0,0 +1,66 @@ +import * as React from 'react'; +import { ContainerModel } from '../../../Interfaces/ContainerModel'; +import { getDepth, MakeIterator } from '../../../utils/itertools'; +import { Dimension } from './Dimension'; + +interface IDimensionLayerProps { + isHidden: boolean + roots: ContainerModel | ContainerModel[] | null +} + +const GAP: number = 50; + +const getDimensionsNodes = (root: ContainerModel): React.ReactNode[] => { + const it = MakeIterator(root); + const dimensions: React.ReactNode[] = []; + for (const container of it) { + // WARN: this might be dangerous later when using other units/rules + const width = Number(container.properties.width); + + const id = `dim-${container.properties.id}`; + const xStart: number = container.properties.x; + const xEnd = xStart + width; + const y = -(GAP * (getDepth(container) + 1)); + const strokeWidth = 1; + const text = width.toString(); + dimensions.push( + + ); + } + return dimensions; +}; + +/** + * A layer containing all dimension + * + * @deprecated In order to avoid adding complexity + * with computing the position in a group hierarchy, + * use Dimension directly inside the Container, + * Currently it is glitched as + * it does not take parents into account, + * and will not work correctly + * @param props + * @returns + */ +export const DimensionLayer: React.FC = (props: IDimensionLayerProps) => { + let dimensions: React.ReactNode[] = []; + if (Array.isArray(props.roots)) { + props.roots.forEach(child => { + dimensions.concat(getDimensionsNodes(child)); + }); + } else if (props.roots !== null) { + dimensions = getDimensionsNodes(props.roots); + } + return ( + + { dimensions } + + ); +}; diff --git a/src/Interfaces/AvailableContainer.ts b/src/Interfaces/AvailableContainer.ts index b328b0a..d7bb22f 100644 --- a/src/Interfaces/AvailableContainer.ts +++ b/src/Interfaces/AvailableContainer.ts @@ -1,11 +1,9 @@ import React from 'react'; -import { XPositionReference } from '../Enums/XPositionReference'; /** Model of available container used in application configuration */ export interface AvailableContainer { Type: string Width: number Height: number - XPositionReference?: XPositionReference Style: React.CSSProperties } diff --git a/src/Interfaces/Properties.ts b/src/Interfaces/Properties.ts index 6f2f32e..ea5f54e 100644 --- a/src/Interfaces/Properties.ts +++ b/src/Interfaces/Properties.ts @@ -1,5 +1,4 @@ import * as React from 'react'; -import { XPositionReference } from '../Enums/XPositionReference'; export default interface Properties extends React.CSSProperties { id: string @@ -7,5 +6,4 @@ export default interface Properties extends React.CSSProperties { x: number y: number isRigidBody: boolean - XPositionReference?: XPositionReference } diff --git a/src/utils/default.ts b/src/utils/default.ts index 51c1d7a..a117ef0 100644 --- a/src/utils/default.ts +++ b/src/utils/default.ts @@ -36,5 +36,3 @@ export const DEFAULT_MAINCONTAINER_PROPS: Properties = { fillOpacity: 0, stroke: 'black' }; - -export const NOTCHES_LENGTH = 4; diff --git a/test-server/http.js b/test-server/http.js index 69088c9..c4f3238 100644 --- a/test-server/http.js +++ b/test-server/http.js @@ -76,6 +76,9 @@ const GetSVGLayoutConfiguration = () => { fillOpacity: 0, borderWidth: 2, stroke: 'blue', + transform: 'translateX(-50%)', + transformOrigin: 'center', + transformBox: 'fill-box' } } ],