2019-10-01 20:07:43 +00:00
|
|
|
import React, { useContext } from "react";
|
2019-09-22 20:25:05 +00:00
|
|
|
import styled from "styled-components";
|
2019-10-02 19:42:25 +00:00
|
|
|
import { Rnd } from "react-rnd";
|
|
|
|
|
import { XYCoord } from "react-dnd";
|
2019-09-22 20:25:05 +00:00
|
|
|
import { WidgetProps, WidgetOperations } from "../widgets/BaseWidget";
|
2019-10-01 20:07:43 +00:00
|
|
|
import { ContainerProps, ParentBoundsContext } from "./ContainerComponent";
|
2019-10-03 15:38:46 +00:00
|
|
|
import { ResizingContext } from "./DraggableComponent";
|
2019-10-03 16:24:29 +00:00
|
|
|
import { WidgetFunctionsContext } from "../pages/Editor";
|
2019-09-22 20:25:05 +00:00
|
|
|
|
|
|
|
|
export type ResizableComponentProps = WidgetProps & ContainerProps;
|
|
|
|
|
|
2019-10-02 19:42:25 +00:00
|
|
|
const ResizableContainer = styled(Rnd)`
|
2019-10-01 20:07:43 +00:00
|
|
|
position: relative;
|
|
|
|
|
z-index: 10;
|
2019-09-22 20:25:05 +00:00
|
|
|
border: ${props => {
|
|
|
|
|
return Object.values(props.theme.borders[0]).join(" ");
|
|
|
|
|
}};
|
2019-10-01 20:07:43 +00:00
|
|
|
&:after,
|
|
|
|
|
&:before {
|
|
|
|
|
content: "";
|
|
|
|
|
position: absolute;
|
2019-10-02 18:13:04 +00:00
|
|
|
width: ${props => props.theme.spaces[2]}px;
|
|
|
|
|
height: ${props => props.theme.spaces[2]}px;
|
|
|
|
|
border-radius: ${props => props.theme.radii[5]}%;
|
2019-10-01 20:07:43 +00:00
|
|
|
z-index: 9;
|
|
|
|
|
background: ${props => props.theme.colors.containerBorder};
|
|
|
|
|
}
|
|
|
|
|
&:after {
|
2019-10-02 18:13:04 +00:00
|
|
|
right: -${props => props.theme.spaces[1]}px;
|
|
|
|
|
top: calc(50% - ${props => props.theme.spaces[1]}px);
|
2019-10-01 20:07:43 +00:00
|
|
|
}
|
2019-09-22 20:25:05 +00:00
|
|
|
|
2019-10-01 20:07:43 +00:00
|
|
|
&:before {
|
2019-10-02 18:13:04 +00:00
|
|
|
left: calc(50% - ${props => props.theme.spaces[1]}px);
|
|
|
|
|
bottom: -${props => props.theme.spaces[1]}px;
|
2019-09-30 03:25:14 +00:00
|
|
|
}
|
|
|
|
|
`;
|
2019-09-22 20:25:05 +00:00
|
|
|
|
|
|
|
|
export const ResizableComponent = (props: ResizableComponentProps) => {
|
2019-10-03 15:38:46 +00:00
|
|
|
const { setIsResizing } = useContext(ResizingContext);
|
2019-10-01 20:07:43 +00:00
|
|
|
const { boundingParent } = useContext(ParentBoundsContext);
|
2019-10-03 16:24:29 +00:00
|
|
|
const { updateWidget } = useContext(WidgetFunctionsContext);
|
2019-10-02 19:42:25 +00:00
|
|
|
let bounds = "body";
|
|
|
|
|
if (boundingParent && boundingParent.current) {
|
|
|
|
|
bounds = "." + boundingParent.current.className.split(" ")[1];
|
|
|
|
|
}
|
2019-09-22 20:25:05 +00:00
|
|
|
const updateSize = (
|
|
|
|
|
e: Event,
|
2019-10-02 19:42:25 +00:00
|
|
|
dir: any,
|
2019-09-22 20:25:05 +00:00
|
|
|
ref: any,
|
|
|
|
|
delta: { width: number; height: number },
|
2019-10-02 19:42:25 +00:00
|
|
|
position: XYCoord,
|
2019-09-22 20:25:05 +00:00
|
|
|
) => {
|
2019-10-03 15:38:46 +00:00
|
|
|
setIsResizing && setIsResizing(false);
|
2019-10-02 19:42:25 +00:00
|
|
|
const leftColumn = props.leftColumn + position.x / props.parentColumnSpace;
|
|
|
|
|
const topRow = props.topRow + position.y / props.parentRowSpace;
|
|
|
|
|
|
|
|
|
|
const rightColumn =
|
|
|
|
|
props.rightColumn + (delta.width + position.x) / props.parentColumnSpace;
|
|
|
|
|
const bottomRow =
|
|
|
|
|
props.bottomRow + (delta.height + position.y) / props.parentRowSpace;
|
|
|
|
|
|
2019-10-03 16:24:29 +00:00
|
|
|
updateWidget &&
|
|
|
|
|
updateWidget(WidgetOperations.RESIZE, props.widgetId, {
|
2019-10-02 19:42:25 +00:00
|
|
|
leftColumn,
|
|
|
|
|
rightColumn,
|
|
|
|
|
topRow,
|
|
|
|
|
bottomRow,
|
|
|
|
|
});
|
2019-09-22 20:25:05 +00:00
|
|
|
};
|
|
|
|
|
return (
|
|
|
|
|
<ResizableContainer
|
2019-10-02 19:42:25 +00:00
|
|
|
position={{
|
|
|
|
|
x: 0,
|
|
|
|
|
y: 0,
|
|
|
|
|
}}
|
2019-09-22 20:25:05 +00:00
|
|
|
size={{
|
2019-09-24 12:36:03 +00:00
|
|
|
width: props.style.componentWidth as number,
|
|
|
|
|
height: props.style.componentHeight as number,
|
2019-09-22 20:25:05 +00:00
|
|
|
}}
|
2019-10-02 19:42:25 +00:00
|
|
|
disableDragging
|
2019-10-02 18:13:04 +00:00
|
|
|
minWidth={props.parentColumnSpace}
|
|
|
|
|
minHeight={props.parentRowSpace}
|
2019-09-22 20:25:05 +00:00
|
|
|
style={{ ...props.style }}
|
|
|
|
|
onResizeStop={updateSize}
|
2019-10-03 15:38:46 +00:00
|
|
|
onResizeStart={() => {
|
|
|
|
|
setIsResizing && setIsResizing(true);
|
|
|
|
|
}}
|
2019-10-02 19:42:25 +00:00
|
|
|
resizeGrid={[props.parentColumnSpace, props.parentRowSpace]}
|
|
|
|
|
bounds={bounds}
|
|
|
|
|
enableResizing={{
|
|
|
|
|
top: true,
|
2019-09-25 21:38:03 +00:00
|
|
|
right: true,
|
|
|
|
|
bottom: true,
|
2019-10-02 19:42:25 +00:00
|
|
|
left: true,
|
2019-09-25 21:38:03 +00:00
|
|
|
topRight: false,
|
|
|
|
|
topLeft: false,
|
2019-10-02 19:42:25 +00:00
|
|
|
bottomRight: true,
|
2019-10-01 20:07:43 +00:00
|
|
|
bottomLeft: false,
|
2019-09-25 21:38:03 +00:00
|
|
|
}}
|
2019-09-22 20:25:05 +00:00
|
|
|
>
|
|
|
|
|
{props.children}
|
|
|
|
|
</ResizableContainer>
|
|
|
|
|
);
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
export default ResizableComponent;
|