refactor(general): fit view in store to prevent flickering, rename onLoad => onPaneReady

This commit is contained in:
moklick
2021-12-09 07:24:45 +01:00
parent 3a52efbb1f
commit 88582a86cc
17 changed files with 96 additions and 100 deletions
+6 -3
View File
@@ -28,7 +28,7 @@ import {
} from '../types';
import { getHandleBounds } from '../components/Nodes/utils';
import { createSelectionChange, getSelectionChanges } from '../utils/changes';
import { createNodeInternals, createPositionChange, isParentSelected } from './utils';
import { createNodeInternals, createPositionChange, fitView, isParentSelected } from './utils';
import initialState from './initialState';
const { Provider, useStore, useStoreApi } = createContext<ReactFlowState>();
@@ -46,7 +46,7 @@ const createStore = () =>
set({ edges });
},
updateNodeDimensions: (updates: NodeDimensionUpdate[]) => {
const { onNodesChange, transform, nodeInternals } = get();
const { onNodesChange, transform, nodeInternals, fitViewOnInit } = get();
const changes: NodeChange[] = updates.reduce<NodeChange[]>((res, update) => {
const node = nodeInternals.get(update.id);
@@ -78,7 +78,9 @@ const createStore = () =>
return res;
}, []);
set({ nodeInternals: new Map(nodeInternals) });
const fitViewOnInitDone = fitViewOnInit && fitView(get);
set({ nodeInternals: new Map(nodeInternals), fitViewOnInitDone });
if (changes?.length > 0) {
onNodesChange?.(changes);
@@ -234,6 +236,7 @@ const createStore = () =>
setOnNodesChange: (onNodesChange: OnNodesChange) => set({ onNodesChange }),
setOnEdgesChange: (onEdgesChange: OnEdgesChange) => set({ onEdgesChange }),
reset: () => set({ ...initialState }),
setFitViewOnInit: (fitViewOnInit: boolean) => set({ fitViewOnInit }),
}));
export { Provider, useStore, createStore, useStoreApi };
+3
View File
@@ -39,6 +39,9 @@ const initialState: ReactFlowStore = {
multiSelectionActive: false,
reactFlowVersion: typeof __REACT_FLOW_VERSION__ !== 'undefined' ? __REACT_FLOW_VERSION__ : '-',
fitViewOnInit: false,
fitViewOnInitDone: false,
};
export default initialState;
+26
View File
@@ -1,13 +1,17 @@
import { zoomIdentity } from 'd3-zoom';
import { GetState } from 'zustand';
import {
CoordinateExtent,
Node,
NodeDimensionChange,
NodeInternals,
NodeInternalsItem,
ReactFlowState,
XYPosition,
XYZPosition,
} from '../types';
import { clampPosition, isNumeric } from '../utils';
import { getRectOfNodes, getTransformForBounds } from '../utils/graph';
type ParentNodes = Record<string, boolean>;
@@ -172,3 +176,25 @@ export function createPositionChange({
return change;
}
export function fitView(get: GetState<ReactFlowState>) {
let { nodeInternals, width, height, minZoom, maxZoom, d3Zoom, d3Selection, fitViewOnInitDone, fitViewOnInit } = get();
if (fitViewOnInit && !fitViewOnInitDone && d3Zoom && d3Selection) {
const rootNodes = Array.from(nodeInternals)
.filter(([_, n]) => !n.parentNode)
.map(([_, n]) => n);
const nodesInitialized = rootNodes.every((n) => n.width && n.height);
if (rootNodes.length > 0 && nodesInitialized) {
const bounds = getRectOfNodes(rootNodes);
const [x, y, zoom] = getTransformForBounds(bounds, width, height, minZoom ?? 0.5, maxZoom ?? 2);
const nextTransform = zoomIdentity.translate(x, y).scale(zoom);
d3Zoom.transform(d3Selection, nextTransform);
fitViewOnInitDone = true;
}
}
return fitViewOnInitDone;
}