Show grid when resizing

This commit is contained in:
Abhinav Jha 2019-10-08 18:01:58 +05:30
parent f04f275d75
commit 023cf4e638
5 changed files with 66 additions and 50 deletions

View File

@ -27,6 +27,7 @@ type DragLayerProps = {
isOver: boolean; isOver: boolean;
parentRows?: number; parentRows?: number;
parentCols?: number; parentCols?: number;
isResizing?: boolean;
}; };
const DragLayerComponent = (props: DragLayerProps) => { const DragLayerComponent = (props: DragLayerProps) => {
@ -55,7 +56,7 @@ const DragLayerComponent = (props: DragLayerProps) => {
: widget.rightColumn - widget.leftColumn; : widget.rightColumn - widget.leftColumn;
widgetHeight = widget.rows ? widget.rows : widget.bottomRow - widget.topRow; widgetHeight = widget.rows ? widget.rows : widget.bottomRow - widget.topRow;
} }
if (!isDragging || !props.visible) { if ((!isDragging || !props.visible) && !props.isResizing) {
return null; return null;
} }
return ( return (
@ -64,7 +65,7 @@ const DragLayerComponent = (props: DragLayerProps) => {
rowHeight={props.parentRowHeight} rowHeight={props.parentRowHeight}
columnWidth={props.parentColumnWidth} columnWidth={props.parentColumnWidth}
setBounds={props.onBoundsUpdate} setBounds={props.onBoundsUpdate}
showGrid={isDragging && props.isOver} showGrid={(isDragging && props.isOver) || props.isResizing}
/> />
<DropZone <DropZone
{...props} {...props}

View File

@ -1,4 +1,4 @@
import React, { useContext, createContext, useState, Context } from "react"; import React, { useContext, createContext, Context } from "react";
import styled from "styled-components"; import styled from "styled-components";
import { WidgetProps, WidgetOperations } from "../widgets/BaseWidget"; import { WidgetProps, WidgetOperations } from "../widgets/BaseWidget";
import { useDrag, DragPreviewImage, DragSourceMonitor } from "react-dnd"; import { useDrag, DragPreviewImage, DragSourceMonitor } from "react-dnd";
@ -8,6 +8,7 @@ import { FocusContext } from "../pages/Editor/Canvas";
import { WidgetFunctionsContext } from "../pages/Editor"; import { WidgetFunctionsContext } from "../pages/Editor";
import { ControlIcons } from "../icons/ControlIcons"; import { ControlIcons } from "../icons/ControlIcons";
import { theme } from "../constants/DefaultTheme"; import { theme } from "../constants/DefaultTheme";
import { ResizingContext } from "./DropTargetComponent";
// FontSizes array in DefaultTheme.tsx // FontSizes array in DefaultTheme.tsx
// Change this to toggle the size of delete and move handles. // Change this to toggle the size of delete and move handles.
@ -51,15 +52,15 @@ const deleteControlIcon = ControlIcons.DELETE_CONTROL({
type DraggableComponentProps = WidgetProps & ContainerProps; type DraggableComponentProps = WidgetProps & ContainerProps;
export const RnDContext: Context<{ export const DraggingContext: Context<{
setIsResizing?: Function;
isDragging?: boolean; isDragging?: boolean;
}> = createContext({}); }> = createContext({});
const DraggableComponent = (props: DraggableComponentProps) => { const DraggableComponent = (props: DraggableComponentProps) => {
const { isFocused, setFocus } = useContext(FocusContext); const { isFocused, setFocus } = useContext(FocusContext);
const { updateWidget } = useContext(WidgetFunctionsContext); const { updateWidget } = useContext(WidgetFunctionsContext);
const [isResizing, setIsResizing] = useState(false); const { isResizing } = useContext(ResizingContext);
const deleteWidget = () => { const deleteWidget = () => {
updateWidget && updateWidget &&
updateWidget(WidgetOperations.DELETE, props.widgetId, { updateWidget(WidgetOperations.DELETE, props.widgetId, {
@ -77,7 +78,7 @@ const DraggableComponent = (props: DraggableComponentProps) => {
}); });
return ( return (
<RnDContext.Provider value={{ setIsResizing, isDragging }}> <DraggingContext.Provider value={{ isDragging }}>
<DragPreviewImage src={blankImage} connect={preview} /> <DragPreviewImage src={blankImage} connect={preview} />
<DraggableWrapper <DraggableWrapper
ref={drag} ref={drag}
@ -112,7 +113,7 @@ const DraggableComponent = (props: DraggableComponentProps) => {
{deleteControlIcon} {deleteControlIcon}
</DeleteControl> </DeleteControl>
</DraggableWrapper> </DraggableWrapper>
</RnDContext.Provider> </DraggingContext.Provider>
); );
}; };

View File

@ -1,4 +1,4 @@
import React, { useState, useContext } from "react"; import React, { useState, useContext, createContext, Context } from "react";
import { WidgetProps } from "../widgets/BaseWidget"; import { WidgetProps } from "../widgets/BaseWidget";
import { OccupiedSpaceContext } from "../widgets/ContainerWidget"; import { OccupiedSpaceContext } from "../widgets/ContainerWidget";
import { WidgetConfigProps } from "../reducers/entityReducers/widgetConfigReducer"; import { WidgetConfigProps } from "../reducers/entityReducers/widgetConfigReducer";
@ -25,9 +25,15 @@ type DropTargetBounds = {
height: number; height: number;
}; };
export const ResizingContext: Context<{
isResizing?: boolean;
setIsResizing?: Function;
}> = createContext({});
export const DropTargetComponent = (props: DropTargetComponentProps) => { export const DropTargetComponent = (props: DropTargetComponentProps) => {
// Hook to keep the offset of the drop target container in state // Hook to keep the offset of the drop target container in state
const [dropTargetOffset, setDropTargetOffset] = useState({ x: 0, y: 0 }); const [dropTargetOffset, setDropTargetOffset] = useState({ x: 0, y: 0 });
const [isResizing, setIsResizing] = useState(false);
const { updateWidget } = useContext(WidgetFunctionsContext); const { updateWidget } = useContext(WidgetFunctionsContext);
const occupiedSpaces = useContext(OccupiedSpaceContext); const occupiedSpaces = useContext(OccupiedSpaceContext);
const { setFocus } = useContext(FocusContext); const { setFocus } = useContext(FocusContext);
@ -97,35 +103,38 @@ export const DropTargetComponent = (props: DropTargetComponentProps) => {
}; };
return ( return (
<div <ResizingContext.Provider value={{ isResizing, setIsResizing }}>
onClick={handleFocus} <div
ref={drop} onClick={handleFocus}
style={{ ref={drop}
position: "relative", style={{
left: 0, position: "relative",
height: props.isRoot left: 0,
? props.style.componentHeight + (props.style.heightUnit || "px") height: props.isRoot
: "100%", ? props.style.componentHeight + (props.style.heightUnit || "px")
width: props.isRoot : "100%",
? props.style.componentWidth + (props.style.widthUnit || "px") width: props.isRoot
: "100%", ? props.style.componentWidth + (props.style.widthUnit || "px")
top: 0, : "100%",
}} top: 0,
> }}
{props.children} >
<DragLayerComponent {props.children}
parentOffset={dropTargetOffset} <DragLayerComponent
parentRowHeight={props.snapRowSpace} parentOffset={dropTargetOffset}
parentColumnWidth={props.snapColumnSpace} parentRowHeight={props.snapRowSpace}
visible={isOver} parentColumnWidth={props.snapColumnSpace}
isOver={isExactlyOver} visible={isOver || isResizing}
dropTargetOffset={dropTargetOffset} isOver={isExactlyOver}
occupiedSpaces={occupiedSpaces} dropTargetOffset={dropTargetOffset}
onBoundsUpdate={handleBoundsUpdate} occupiedSpaces={occupiedSpaces}
parentRows={props.snapRows} onBoundsUpdate={handleBoundsUpdate}
parentCols={props.snapColumns} parentRows={props.snapRows}
/> parentCols={props.snapColumns}
</div> isResizing={isResizing}
/>
</div>
</ResizingContext.Provider>
); );
}; };

View File

@ -5,7 +5,7 @@ type DropTargetMaskProps = {
rowHeight: number; rowHeight: number;
columnWidth: number; columnWidth: number;
setBounds?: Function; setBounds?: Function;
showGrid: boolean; showGrid?: boolean;
}; };
export const DropTargetMaskWrapper = styled.div<DropTargetMaskProps>` export const DropTargetMaskWrapper = styled.div<DropTargetMaskProps>`

View File

@ -7,8 +7,9 @@ import { OccupiedSpaceContext } from "../widgets/ContainerWidget";
import { ContainerProps, ParentBoundsContext } from "./ContainerComponent"; import { ContainerProps, ParentBoundsContext } from "./ContainerComponent";
import { isDropZoneOccupied } from "../utils/WidgetPropsUtils"; import { isDropZoneOccupied } from "../utils/WidgetPropsUtils";
import { FocusContext } from "../pages/Editor/Canvas"; import { FocusContext } from "../pages/Editor/Canvas";
import { RnDContext } from "./DraggableComponent"; import { DraggingContext } from "./DraggableComponent";
import { WidgetFunctionsContext } from "../pages/Editor"; import { WidgetFunctionsContext } from "../pages/Editor";
import { ResizingContext } from "./DropTargetComponent";
import { import {
theme, theme,
getColorWithOpacity, getColorWithOpacity,
@ -87,11 +88,13 @@ const ResizableContainer = styled(Rnd)`
`; `;
export const ResizableComponent = (props: ResizableComponentProps) => { export const ResizableComponent = (props: ResizableComponentProps) => {
const { setIsResizing, isDragging } = useContext(RnDContext); const { isDragging } = useContext(DraggingContext);
const { setIsResizing } = useContext(ResizingContext);
const { boundingParent } = useContext(ParentBoundsContext); const { boundingParent } = useContext(ParentBoundsContext);
const { updateWidget } = useContext(WidgetFunctionsContext); const { updateWidget } = useContext(WidgetFunctionsContext);
const { isFocused, setFocus } = useContext(FocusContext); const { isFocused, setFocus } = useContext(FocusContext);
const occupiedSpaces = useContext(OccupiedSpaceContext); const occupiedSpaces = useContext(OccupiedSpaceContext);
const [isColliding, setIsColliding] = useState(false); const [isColliding, setIsColliding] = useState(false);
let bounds = "body"; let bounds = "body";
@ -142,6 +145,7 @@ export const ResizableComponent = (props: ResizableComponentProps) => {
) => { ) => {
setIsResizing && setIsResizing(false); setIsResizing && setIsResizing(false);
setFocus && setFocus(props.widgetId); setFocus && setFocus(props.widgetId);
const leftColumn = props.leftColumn + position.x / props.parentColumnSpace; const leftColumn = props.leftColumn + position.x / props.parentColumnSpace;
const topRow = props.topRow + position.y / props.parentRowSpace; const topRow = props.topRow + position.y / props.parentRowSpace;
@ -161,6 +165,8 @@ export const ResizableComponent = (props: ResizableComponentProps) => {
} }
setIsColliding(false); setIsColliding(false);
}; };
const canResize = !isDragging && isFocused === props.widgetId;
return ( return (
<ResizableContainer <ResizableContainer
position={{ position={{
@ -192,16 +198,15 @@ export const ResizableComponent = (props: ResizableComponentProps) => {
resizeGrid={[props.parentColumnSpace, props.parentRowSpace]} resizeGrid={[props.parentColumnSpace, props.parentRowSpace]}
bounds={bounds} bounds={bounds}
resizeHandleStyles={handleStyles} resizeHandleStyles={handleStyles}
resizeHandleWrapperClass="top-of-stacking-context"
enableResizing={{ enableResizing={{
top: true && !isDragging && isFocused === props.widgetId, top: canResize,
right: true && !isDragging && isFocused === props.widgetId, right: canResize,
bottom: true && !isDragging && isFocused === props.widgetId, bottom: canResize,
left: true && !isDragging && isFocused === props.widgetId, left: canResize,
topRight: true && !isDragging && isFocused === props.widgetId, topRight: canResize,
topLeft: true && !isDragging && isFocused === props.widgetId, topLeft: canResize,
bottomRight: true && !isDragging && isFocused === props.widgetId, bottomRight: canResize,
bottomLeft: true && !isDragging && isFocused === props.widgetId, bottomLeft: canResize,
}} }}
> >
{props.children} {props.children}