Skip to content

Commit 154ba27

Browse files
author
Kevin Busch
committed
Refactored effect hooks to track changes on a more granular scale
1 parent 231294c commit 154ba27

2 files changed

Lines changed: 88 additions & 58 deletions

File tree

src/atoms/forms/canvas-sketch/react-canvas-sketch.stories.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ export const reactCanvasSketch = () => (
2323
className={text("Class Name", "")}
2424
containerHeight={number("Container Height", 700)}
2525
containerWidth={number("Container Width", 700)}
26-
onAddedStroke={(strokeSettings: CanvasDrawToolSettings) => { console.log(`onAddedStroke: ${JSON.stringify(strokeSettings)}`) }}
26+
onAddedStroke={(strokeSettings: CanvasDrawToolSettings) => { console.log(`STORYBOOK - onAddedStroke: ${JSON.stringify(strokeSettings)}`) }}
2727
redrawIncrement={number("Redraw Trigger Increment", 1)}
2828
canvasToolType={select("Tool Type", canvasToolTypes, CanvasToolType.pencil)}
2929
showCanvasBorder={boolean("Show Border", true)}

src/atoms/forms/canvas-sketch/react-canvas-sketch.tsx

Lines changed: 87 additions & 57 deletions
Original file line numberDiff line numberDiff line change
@@ -105,63 +105,57 @@ const ReactCanvasSketch: React.FunctionComponent<ReactCanvasSketchProps> = (
105105
const htmlCanvasBackgroundImage = React.createRef<HTMLCanvasElement>();
106106
const htmlCanvasSketch = React.createRef<HTMLCanvasElement>();
107107

108-
// track the previous list of objects
109-
const prevValueObjectsRef = React.useRef<CanvasDrawToolSettings[]>();
110-
useEffect(() => {
111-
prevValueObjectsRef.current = props.value.objects;
112-
});
113-
const prevValueObjects = prevValueObjectsRef.current;
114-
115108
// initialize state
116109
const canvasSketchDefaultInstance: CanvasSketch = null as any;
117110
const [isInitialized, setIsInitialized] = React.useState(false);
118111
const [canvasSketch, setCanvasSketch] = React.useState(canvasSketchDefaultInstance);
119112

120-
// set up effects
113+
// ---------------------------------------------------------------------------------------------
114+
// #region Effect Hooks
115+
// ---------------------------------------------------------------------------------------------
116+
117+
// initialization of canvas sketch - NOTE: Must be before other effects using canvasSketch!
121118
useEffect(() => {
122-
console.log("useEffect: initializing");
123-
if (!isInitialized) {
124-
// set up the default options for the background image
125-
const canvasSketchConfig: CanvasSketchConfig = {
126-
backgroundImage: { src: props.backgroundImageUrl },
127-
backgroundImageCanvas: htmlCanvasBackgroundImage.current as HTMLCanvasElement,
128-
currentObjectIndex: props.value.currentObjectIndex,
129-
objectStack: props.value.objects,
130-
panX: 0,
131-
panY: 0,
132-
scaleFactor: 1,
133-
sketchCanvas: htmlCanvasSketch.current as HTMLCanvasElement,
134-
};
135-
136-
// initialize the canvas sketch object
137-
const newCanvasSketch = new CanvasSketch(canvasSketchConfig);
138-
139-
// set up any default property driven settings
140-
newCanvasSketch.setSelectedTool(props.canvasToolType);
141-
newCanvasSketch.setToolColor(props.toolColor);
142-
newCanvasSketch.setToolWidth(props.toolWidth);
143-
newCanvasSketch.setOnAddedToolStroke(props.onAddedStroke);
144-
145-
// set state
146-
setCanvasSketch(newCanvasSketch);
147-
setIsInitialized(true);
119+
if (isInitialized) {
120+
// already initialized, bail
121+
return;
148122
}
123+
124+
console.log("useEffect: Initializing");
125+
126+
const {
127+
backgroundImageUrl,
128+
value,
129+
} = { ...props };
130+
131+
// set up the default options for the background image
132+
const canvasSketchConfig: CanvasSketchConfig = {
133+
backgroundImage: { src: backgroundImageUrl },
134+
backgroundImageCanvas: htmlCanvasBackgroundImage.current as HTMLCanvasElement,
135+
currentObjectIndex: value.currentObjectIndex,
136+
objectStack: value.objects,
137+
panX: 0,
138+
panY: 0,
139+
scaleFactor: 1,
140+
sketchCanvas: htmlCanvasSketch.current as HTMLCanvasElement,
141+
};
142+
143+
// initialize the canvas sketch object
144+
const newCanvasSketch = new CanvasSketch(canvasSketchConfig);
145+
146+
// set state
147+
setCanvasSketch(newCanvasSketch);
148+
setIsInitialized(true);
149149
}, [
150150
canvasSketch,
151151
htmlCanvasBackgroundImage,
152152
htmlCanvasSketch,
153153
isInitialized,
154-
props.backgroundImageUrl,
155-
props.canvasToolType,
156-
props.onAddedStroke,
157-
props.toolColor,
158-
props.toolWidth,
159-
props.value.currentObjectIndex,
160-
props.value.objects,
154+
props
161155
]);
162156

157+
// cleanup of canvas sketch when unmounting component
163158
useEffect(() => {
164-
console.log("useEffect: canvasSketch");
165159
return () => {
166160
// cleanup on unmount
167161
if (canvasSketch != null) {
@@ -170,12 +164,12 @@ const ReactCanvasSketch: React.FunctionComponent<ReactCanvasSketchProps> = (
170164
}
171165
}, [canvasSketch]);
172166

167+
// redraws current state when dimensions of container or canvas change
173168
useEffect(() => {
174169
if (canvasSketch == null) {
175170
return;
176171
}
177172
canvasSketch.redrawCurrentState();
178-
179173
}, [
180174
canvasSketch,
181175
props.canvasHeight,
@@ -184,53 +178,89 @@ const ReactCanvasSketch: React.FunctionComponent<ReactCanvasSketchProps> = (
184178
props.containerWidth,
185179
]);
186180

181+
// redraw the sketch canvas when current object index or objects changes
187182
useEffect(() => {
188183
if (canvasSketch == null) {
189184
return;
190185
}
191-
// Only redraw if currentObjectIndex changes but not the objects list itself. Being done to
192-
// prevent rerenders after every single stroke of the same tool. See following URL for more
193-
// inforamtion on tracking previous state/props using hooks
194-
// https://stackoverflow.com/questions/55724642/react-useeffect-hook-when-only-one-of-the-effects-deps-changes-but-not-the-oth
195-
if (prevValueObjects === props.value.objects) {
196-
canvasSketch.redrawSketchAt(props.value.objects, props.value.currentObjectIndex);
197-
}
198-
}, [props.value.currentObjectIndex, props.value.objects, canvasSketch, prevValueObjects]);
199186

187+
canvasSketch.redrawSketchAt(props.value.objects, props.value.currentObjectIndex);
188+
}, [
189+
canvasSketch,
190+
props.value.currentObjectIndex,
191+
props.value.objects,
192+
]);
193+
194+
// redraw the sketch canvas when redraw increment changes
200195
useEffect(() => {
201196
if (canvasSketch == null) {
202197
return;
203198
}
204-
canvasSketch.redrawSketchAt(props.value.objects, props.value.currentObjectIndex);
205-
}, [props.redrawIncrement, canvasSketch, props.value.objects, props.value.currentObjectIndex]);
206199

200+
const { value } = { ...props };
201+
202+
canvasSketch.redrawSketchAt(value.objects, value.currentObjectIndex);
203+
}, [
204+
props,
205+
canvasSketch
206+
]);
207+
208+
// redraw the background image when it changes
207209
useEffect(() => {
208210
if (canvasSketch == null) {
209211
return;
210212
}
211213
canvasSketch.redrawBackgroundImageUsing(props.backgroundImageUrl);
212-
}, [props.backgroundImageUrl, canvasSketch]);
214+
}, [
215+
props.backgroundImageUrl,
216+
canvasSketch
217+
]);
213218

219+
// set on added stroke when changes
220+
useEffect(() => {
221+
if (canvasSketch == null) {
222+
return;
223+
}
224+
canvasSketch.setOnAddedToolStroke(props.onAddedStroke);
225+
}, [
226+
props.onAddedStroke,
227+
canvasSketch
228+
]);
229+
230+
// set tool color when it changes
214231
useEffect(() => {
215232
if (canvasSketch == null) {
216233
return;
217234
}
218235
canvasSketch.setToolColor(props.toolColor);
219-
}, [props.toolColor, canvasSketch]);
236+
}, [
237+
props.toolColor,
238+
canvasSketch
239+
]);
220240

241+
// set tool width when it changes
221242
useEffect(() => {
222243
if (canvasSketch == null) {
223244
return;
224245
}
225246
canvasSketch.setToolWidth(props.toolWidth);
226-
}, [props.toolWidth, canvasSketch]);
247+
}, [
248+
props.toolWidth,
249+
canvasSketch
250+
]);
227251

252+
// set selected tool when it changes
228253
useEffect(() => {
229254
if (canvasSketch == null) {
230255
return;
231256
}
232257
canvasSketch.setSelectedTool(props.canvasToolType);
233-
}, [props.canvasToolType, canvasSketch]);
258+
}, [
259+
props.canvasToolType,
260+
canvasSketch
261+
]);
262+
263+
// #endregion Effect Hooks
234264

235265

236266
// configure styles for elemtns

0 commit comments

Comments
 (0)