From 8408b126454865c30129b981231b4fe76733bed8 Mon Sep 17 00:00:00 2001 From: bpmn-io-bot Date: Wed, 10 Jan 2024 16:14:33 +0000 Subject: [PATCH 1/4] chore(CI): updated snapshots [skip ci] --- .../carbon-styles-1-chromium-linux.png | Bin 32834 -> 41301 bytes 1 file changed, 0 insertions(+), 0 deletions(-) diff --git a/e2e/visual/carbon-styles.spec.js-snapshots/carbon-styles-1-chromium-linux.png b/e2e/visual/carbon-styles.spec.js-snapshots/carbon-styles-1-chromium-linux.png index 526183116c89f519ded8d21df074d1a5290d14f7..aac62955c0b97ae3efd6687d2a91de9856e33022 100644 GIT binary patch literal 41301 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 literal 32834 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 TKdeci*Eaal@Qaks4}bet1}sx` From 0918c5e892dc99dca15586431647b18d25e129af Mon Sep 17 00:00:00 2001 From: Valentin Serra Date: Fri, 22 Dec 2023 10:07:11 +0100 Subject: [PATCH 2/4] chore: fix missing react hook deps Related to hto#444 --- .../slot-fill/SlotFillRoot.js | 13 +- .../src/render/components/FormEditor.js | 135 ++++++++++-------- .../src/render/hooks/useDebounce.js | 8 +- .../src/components/PlaygroundRoot.js | 12 +- .../form-js-viewer/src/render/Renderer.js | 6 +- .../form-fields/parts/SimpleSelect.js | 2 +- 6 files changed, 99 insertions(+), 77 deletions(-) diff --git a/packages/form-js-editor/src/features/render-injection/slot-fill/SlotFillRoot.js b/packages/form-js-editor/src/features/render-injection/slot-fill/SlotFillRoot.js index 1ed763d52..72be9c78b 100644 --- a/packages/form-js-editor/src/features/render-injection/slot-fill/SlotFillRoot.js +++ b/packages/form-js-editor/src/features/render-injection/slot-fill/SlotFillRoot.js @@ -2,19 +2,26 @@ import FillContext from './FillContext'; import SlotContext from './SlotContext'; import { useMemo, useState } from 'preact/hooks'; +const noop = () => {}; + export default (props) => { const [ fills, setFills ] = useState([]); + const { + onSetFill = noop, + onRemoveFill = noop + } = props; + const fillContext = useMemo(() => ({ addFill: (fill) => { setFills((fills) => [ ...fills.filter((f) => f.id !== fill.id), fill ]); - props.onSetFill && props.onSetFill(fill); + onSetFill(fill); }, removeFill: (id) => { setFills((fills) => fills.filter((f) => f.id !== id)); - props.onRemoveFill && props.onRemoveFill(id); + onRemoveFill(id); } - }), []); + }), [ onRemoveFill, onSetFill ]); const slotContext = useMemo(() => ({ fills }), [ fills ]); diff --git a/packages/form-js-editor/src/render/components/FormEditor.js b/packages/form-js-editor/src/render/components/FormEditor.js index 77ca3b8bc..b253e0514 100644 --- a/packages/form-js-editor/src/render/components/FormEditor.js +++ b/packages/form-js-editor/src/render/components/FormEditor.js @@ -110,24 +110,25 @@ function Element(props) { const [ hovered, setHovered ] = useState(false); - function scrollIntoView({ selection }) { - if (!selection || selection.id !== id || !ref.current) { - return; - } + useEffect(() => { - const elementBounds = ref.current.getBoundingClientRect(), - containerBounds = formEditor._container.getBoundingClientRect(); + function scrollIntoView({ selection }) { + if (!selection || selection.id !== id || !ref.current) { + return; + } - if (elementBounds.top < 0 || elementBounds.top > containerBounds.bottom) { - ref.current.scrollIntoView(); + const elementBounds = ref.current.getBoundingClientRect(), + containerBounds = formEditor._container.getBoundingClientRect(); + + if (elementBounds.top < 0 || elementBounds.top > containerBounds.bottom) { + ref.current.scrollIntoView(); + } } - } - useEffect(() => { eventBus.on('selection.changed', scrollIntoView); return () => eventBus.off('selection.changed', scrollIntoView); - }, [ id ]); + }, [ eventBus, formEditor._container, id ]); useLayoutEffect(() => { if (selection.isSelected(field)) { @@ -320,7 +321,7 @@ function Column(props) { ); } -export default function FormEditor(props) { +export default function FormEditor() { const dragging = useService('dragging'), eventBus = useService('eventBus'), formEditor = useService('formEditor'), @@ -339,6 +340,8 @@ export default function FormEditor(props) { const [ , setSelection ] = useState(schema); + const [ hasInitialized, setHasInitialized ] = useState(false); + useEffect(() => { function handleSelectionChanged(event) { setSelection(event.selection || schema); @@ -346,12 +349,14 @@ export default function FormEditor(props) { eventBus.on('selection.changed', handleSelectionChanged); - setSelection(selection.get() || schema); - return () => { eventBus.off('selection.changed', handleSelectionChanged); }; - }, [ schema, selection ]); + }, [ eventBus, schema ]); + + useEffect(() => { + setSelection(selection.get() || schema); + }, [ selection, schema ]); const [ drake, setDrake ] = useState(null); @@ -424,11 +429,17 @@ export default function FormEditor(props) { // fire event after render to notify interested parties useEffect(() => { + + if (hasInitialized) { + return; + } + + setHasInitialized(true); eventBus.fire('rendered'); // keep deprecated event to ensure backward compatibility eventBus.fire('formEditor.rendered'); - }, []); + }, [ eventBus, hasInitialized ]); const formRenderContext = useMemo(() => ({ Children, @@ -523,69 +534,69 @@ function CreatePreview(props) { const formFields = useService('formFields'); - function handleCloned(clone, original, type) { - - const fieldType = clone.dataset.fieldType; + useEffect(() => { + if (!drake) { + return; + } - // (1) field preview - if (fieldType) { + function handleCloned(clone, original, type) { - const paletteEntry = findPaletteEntry(fieldType, formFields); + const fieldType = clone.dataset.fieldType; - if (!paletteEntry) { - return; - } + // (1) field preview + if (fieldType) { - const { label } = paletteEntry; + const paletteEntry = findPaletteEntry(fieldType, formFields); - const Icon = getPaletteIcon(paletteEntry); + if (!paletteEntry) { + return; + } - clone.innerHTML = ''; + const { label } = paletteEntry; - clone.class = 'gu-mirror'; - clone.classList.add('fjs-field-preview-container'); + const Icon = getPaletteIcon(paletteEntry); - if (original.classList.contains('fjs-palette-field')) { + clone.innerHTML = ''; - // default to auto columns when creating from palette - clone.classList.add('cds--col'); - } + clone.class = 'gu-mirror'; + clone.classList.add('fjs-field-preview-container'); - // todo(pinussilvestrus): dragula, how to mitigate cursor position - // https://github.com/bevacqua/dragula/issues/285 - render( - , - clone - ); - } else { - - // (2) row preview - - // remove elements from copy (context pad, row dragger, ...) - [ - 'fjs-context-pad', - 'fjs-row-dragger', - 'fjs-debug-columns' - ].forEach(cls => { - const cloneNode = clone.querySelectorAll('.' + cls); - cloneNode.length && cloneNode.forEach(e => e.remove()); - }); + if (original.classList.contains('fjs-palette-field')) { - // mirror grid - clone.classList.add('cds--grid'); - clone.classList.add('cds--grid--condensed'); - } - } + // default to auto columns when creating from palette + clone.classList.add('cds--col'); + } - useEffect(() => { - if (!drake) { - return; + // todo(pinussilvestrus): dragula, how to mitigate cursor position + // https://github.com/bevacqua/dragula/issues/285 + render( + , + clone + ); + } else { + + // (2) row preview + + // remove elements from copy (context pad, row dragger, ...) + [ + 'fjs-context-pad', + 'fjs-row-dragger', + 'fjs-debug-columns' + ].forEach(cls => { + const cloneNode = clone.querySelectorAll('.' + cls); + cloneNode.length && cloneNode.forEach(e => e.remove()); + }); + + // mirror grid + clone.classList.add('cds--grid'); + clone.classList.add('cds--grid--condensed'); + } } drake.on('cloned', handleCloned); return () => drake.off('cloned', handleCloned); - }, [ drake ]); + }, [ drake, formFields ]); return null; } diff --git a/packages/form-js-editor/src/render/hooks/useDebounce.js b/packages/form-js-editor/src/render/hooks/useDebounce.js index 1a51b654f..5c4ac076b 100644 --- a/packages/form-js-editor/src/render/hooks/useDebounce.js +++ b/packages/form-js-editor/src/render/hooks/useDebounce.js @@ -5,14 +5,16 @@ import { import useService from './useService'; - -export default function useDebounce(fn, dependencies = []) { +/** + * @param {Function} fn - function to debounce + */ +export default function useDebounce(fn) { const debounce = useService('debounce'); const callback = useMemo(() => { return debounce(fn); - }, dependencies); + }, [ debounce, fn ]); // cleanup async side-effect if callback #flush is provided. useEffect(() => { diff --git a/packages/form-js-playground/src/components/PlaygroundRoot.js b/packages/form-js-playground/src/components/PlaygroundRoot.js index 4b242ff31..94e1c449c 100644 --- a/packages/form-js-playground/src/components/PlaygroundRoot.js +++ b/packages/form-js-playground/src/components/PlaygroundRoot.js @@ -33,7 +33,9 @@ export function PlaygroundRoot(props) { editorProperties = {}, viewerAdditionalModules = [], editorAdditionalModules = [], - propertiesPanel: propertiesPanelConfig = {} + propertiesPanel: propertiesPanelConfig = {}, + onInit: onPlaygroundInit, + onStateChanged } = props; const { @@ -66,7 +68,7 @@ export function PlaygroundRoot(props) { // pipe to playground API useEffect(() => { - props.onInit({ + onPlaygroundInit({ attachDataContainer: (node) => dataEditorRef.current.attachTo(node), attachEditorContainer: (node) => formEditorRef.current.attachTo(node), attachFormContainer: (node) => formRef.current.attachTo(node), @@ -82,7 +84,7 @@ export function PlaygroundRoot(props) { setSchema: setInitialSchema, saveSchema: () => formEditorRef.current.saveSchema() }); - }); + }, [ onPlaygroundInit ]); useEffect(() => { setInitialSchema(props.schema || {}); @@ -230,11 +232,11 @@ export function PlaygroundRoot(props) { }, [ resultData ]); useEffect(() => { - props.onStateChanged({ + onStateChanged && onStateChanged({ schema, data }); - }, [ schema, data ]); + }, [ onStateChanged, schema, data ]); const handleDownload = useCallback(() => { diff --git a/packages/form-js-viewer/src/render/Renderer.js b/packages/form-js-viewer/src/render/Renderer.js index e3fe20781..78255d268 100644 --- a/packages/form-js-viewer/src/render/Renderer.js +++ b/packages/form-js-viewer/src/render/Renderer.js @@ -34,7 +34,7 @@ export default function Renderer(config, eventBus, form, injector) { setState(newState); }); - const onChange = useCallback((update) => form._update(update), [ form ]); + const onChange = useCallback((update) => form._update(update), []); const { properties } = state; @@ -44,9 +44,9 @@ export default function Renderer(config, eventBus, form, injector) { if (!readOnly) { form.submit(); } - }, [ form, readOnly ]); + }, [ readOnly ]); - const onReset = useCallback(() => form.reset(), [ form ]); + const onReset = useCallback(() => form.reset(), []); const { schema } = state; diff --git a/packages/form-js-viewer/src/render/components/form-fields/parts/SimpleSelect.js b/packages/form-js-viewer/src/render/components/form-fields/parts/SimpleSelect.js index b2521308b..1956e767e 100644 --- a/packages/form-js-viewer/src/render/components/form-fields/parts/SimpleSelect.js +++ b/packages/form-js-viewer/src/render/components/form-fields/parts/SimpleSelect.js @@ -53,7 +53,7 @@ export default function SimpleSelect(props) { ds.displayCross = ds.componentReady && value !== null && value !== undefined; ds.displayDropdown = !disabled && !readonly && isDropdownExpanded; return ds; - }, [ disabled, isDropdownExpanded, loadState, value ]); + }, [ disabled, isDropdownExpanded, loadState, readonly, value ]); const onMouseDown = useCallback((e) => { const input = inputRef.current; From 7cfa735d4927444c52e5529bdcc5c6f403746ef3 Mon Sep 17 00:00:00 2001 From: Valentin Serra Date: Tue, 9 Jan 2024 06:00:09 +0100 Subject: [PATCH 3/4] chore: no complex expressions in preact dependency array Related to hto#444 --- .../src/features/repeatRender/RepeatRenderManager.js | 6 +++--- .../src/render/components/FormField.js | 2 +- .../src/render/components/form-fields/Taglist.js | 10 ++++++---- .../components/form-fields/parts/Datepicker.js | 8 ++++++-- .../src/render/hooks/useCleanupMultiSelectValues.js | 9 ++++++--- .../src/render/hooks/useDeepCompareState.js | 12 +++--------- 6 files changed, 25 insertions(+), 22 deletions(-) diff --git a/packages/form-js-viewer/src/features/repeatRender/RepeatRenderManager.js b/packages/form-js-viewer/src/features/repeatRender/RepeatRenderManager.js index ddb3fef5b..5f2454f1e 100644 --- a/packages/form-js-viewer/src/features/repeatRender/RepeatRenderManager.js +++ b/packages/form-js-viewer/src/features/repeatRender/RepeatRenderManager.js @@ -80,10 +80,10 @@ export default class RepeatRenderManager { return ( <> {displayValues.map((value, index) => { - const elementProps = { + const elementProps = useMemo(() => ({ ...restProps, - indexes: { ...(indexes || {}), [ repeaterField.id ]: index }, - }; + indexes: { ...(indexes || {}), [ repeaterField.id ]: index } + }), [ index ]); const localExpressionContextInfo = useMemo(() => ({ data: parentExpressionContextInfo.data, diff --git a/packages/form-js-viewer/src/render/components/FormField.js b/packages/form-js-viewer/src/render/components/FormField.js index 971f1c7f8..ebd5b2bc1 100644 --- a/packages/form-js-viewer/src/render/components/FormField.js +++ b/packages/form-js-viewer/src/render/components/FormField.js @@ -77,7 +77,7 @@ export default function FormField(props) { if (viewerCommands && initialValue) { viewerCommands.updateFieldValidation(field, initialValue, indexes); } - }, [ viewerCommands, field, initialValue, JSON.stringify(indexes) ]); + }, [ viewerCommands, field, initialValue, indexes ]); const hidden = useCondition(field.conditional && field.conditional.hide || null); diff --git a/packages/form-js-viewer/src/render/components/form-fields/Taglist.js b/packages/form-js-viewer/src/render/components/form-fields/Taglist.js index 790c19c12..af7e0d5cc 100644 --- a/packages/form-js-viewer/src/render/components/form-fields/Taglist.js +++ b/packages/form-js-viewer/src/render/components/form-fields/Taglist.js @@ -1,6 +1,6 @@ import { useMemo, useRef, useState } from 'preact/hooks'; -import { useService } from '../../hooks'; +import { useDeepCompareState, useService } from '../../hooks'; import useOptionsAsync, { LOAD_STATES } from '../../hooks/useOptionsAsync'; import useCleanupMultiSelectValues from '../../hooks/useCleanupMultiSelectValues'; import { useGetLabelCorrelation } from '../../hooks/useGetLabelCorrelation'; @@ -35,7 +35,7 @@ export default function Taglist(props) { onBlur, field, readonly, - value : values = [] + value } = props; const { @@ -58,6 +58,9 @@ export default function Taglist(props) { options } = useOptionsAsync(field); + // ensures we render based on array content instead of reference + const values = useDeepCompareState(value || [], []); + useCleanupMultiSelectValues({ field, loadState, @@ -70,7 +73,6 @@ export default function Taglist(props) { const hasOptionsLeft = useMemo(() => options.length > values.length, [ options.length, values.length ]); - // Usage of stringify is necessary here because we want this effect to only trigger when there is a value change to the array const filteredOptions = useMemo(() => { if (loadState !== LOAD_STATES.LOADED) { return []; @@ -82,7 +84,7 @@ export default function Taglist(props) { }; return options.filter(isValidFilteredOption); - }, [ filter, options, JSON.stringify(values), loadState ]); + }, [ filter, options, values, loadState ]); const selectValue = (value) => { diff --git a/packages/form-js-viewer/src/render/components/form-fields/parts/Datepicker.js b/packages/form-js-viewer/src/render/components/form-fields/parts/Datepicker.js index 7f53c711b..2179b3f35 100644 --- a/packages/form-js-viewer/src/render/components/form-fields/parts/Datepicker.js +++ b/packages/form-js-viewer/src/render/components/form-fields/parts/Datepicker.js @@ -6,6 +6,7 @@ import { useCallback, useEffect, useRef, useState } from 'preact/hooks'; import CalendarIcon from '../icons/Calendar.svg'; import InputAdorner from './InputAdorner'; import Label from '../../Label'; +import { useDeepCompareState } from '../../../hooks'; export default function Datepicker(props) { @@ -18,7 +19,7 @@ export default function Datepicker(props) { required, disabled, disallowPassedDates, - date, + date: dateObject, readonly, setDate } = props; @@ -30,6 +31,9 @@ export default function Datepicker(props) { const [ isInputDirty, setIsInputDirty ] = useState(false); const [ forceFocusCalendar, setForceFocusCalendar ] = useState(false); + // ensures we render based on date value instead of reference + const date = useDeepCompareState(dateObject, null); + // shorts the date value back to the source useEffect(() => { @@ -38,7 +42,7 @@ export default function Datepicker(props) { flatpickrInstance.setDate(date, true); setIsInputDirty(false); - }, [ flatpickrInstance, date.toString() ]); + }, [ flatpickrInstance, date ]); useEffect(() => { diff --git a/packages/form-js-viewer/src/render/hooks/useCleanupMultiSelectValues.js b/packages/form-js-viewer/src/render/hooks/useCleanupMultiSelectValues.js index 5c8bbde32..0f65f5587 100644 --- a/packages/form-js-viewer/src/render/hooks/useCleanupMultiSelectValues.js +++ b/packages/form-js-viewer/src/render/hooks/useCleanupMultiSelectValues.js @@ -1,6 +1,7 @@ import { useEffect } from 'preact/hooks'; import { LOAD_STATES } from './useOptionsAsync'; import { hasEqualValue } from '../components/util/sanitizerUtil'; +import useDeepCompareState from './useDeepCompareState'; export default function(props) { @@ -9,10 +10,12 @@ export default function(props) { options, loadState, onChange, - values + values: valuesArray } = props; - // Ensures that the values are always a subset of the possible options + const values = useDeepCompareState(valuesArray, []); + + // ensures that the values are always a subset of the possible options useEffect(() => { if (loadState !== LOAD_STATES.LOADED) { @@ -29,6 +32,6 @@ export default function(props) { }); } - }, [ field, options, onChange, JSON.stringify(values), loadState ]); + }, [ field, options, onChange, values, loadState ]); } \ No newline at end of file diff --git a/packages/form-js-viewer/src/render/hooks/useDeepCompareState.js b/packages/form-js-viewer/src/render/hooks/useDeepCompareState.js index b33e3598c..4cb30e943 100644 --- a/packages/form-js-viewer/src/render/hooks/useDeepCompareState.js +++ b/packages/form-js-viewer/src/render/hooks/useDeepCompareState.js @@ -4,6 +4,7 @@ import { } from 'preact/hooks'; import usePrevious from './usePrevious'; +import isEqual from 'lodash/isEqual'; /** * A custom hook to manage state changes with deep comparison. @@ -18,7 +19,7 @@ export default function useDeepCompareState(value, defaultValue) { const previous = usePrevious(value, defaultValue, [ value ]); - const changed = !compare(previous, value); + const changed = !isEqual(previous, value); useEffect(() => { if (changed) { @@ -27,11 +28,4 @@ export default function useDeepCompareState(value, defaultValue) { }, [ changed, value ]); return state; - -} - -// helpers ////////////////////////// - -function compare(a, b) { - return JSON.stringify(a) === JSON.stringify(b); -} +} \ No newline at end of file From 29e266b00e52f60c820ee52f4d284c5fcaeb5286 Mon Sep 17 00:00:00 2001 From: Valentin Serra Date: Tue, 9 Jan 2024 06:12:26 +0100 Subject: [PATCH 4/4] chore: cleanup custom hooks Related to hto#444 --- .../form-js-editor/src/render/hooks/usePrevious.js | 6 +++--- .../src/render/components/form-fields/Textarea.js | 2 +- .../src/render/components/form-fields/Textfield.js | 2 +- .../src/render/hooks/useCleanupMultiSelectValues.js | 10 +++++----- .../src/render/hooks/useDeepCompareState.js | 2 +- .../src/render/hooks/useFlushDebounce.js | 6 +++--- .../form-js-viewer/src/render/hooks/usePrevious.js | 4 ++-- packages/form-js-viewer/test/helper/preactDebuggers.js | 8 ++++---- 8 files changed, 20 insertions(+), 20 deletions(-) diff --git a/packages/form-js-editor/src/render/hooks/usePrevious.js b/packages/form-js-editor/src/render/hooks/usePrevious.js index 99bc24913..21a3bfbf1 100644 --- a/packages/form-js-editor/src/render/hooks/usePrevious.js +++ b/packages/form-js-editor/src/render/hooks/usePrevious.js @@ -4,10 +4,10 @@ import { } from 'preact/hooks'; -export default function usePrevious(value) { - const ref = useRef(); +export default function usePrevious(value, defaultValue = null) { + const ref = useRef(defaultValue); - useEffect(() => ref.current = value); + useEffect(() => ref.current = value, [ value ]); return ref.current; } \ No newline at end of file diff --git a/packages/form-js-viewer/src/render/components/form-fields/Textarea.js b/packages/form-js-viewer/src/render/components/form-fields/Textarea.js index 3b2fdf5a0..8e0504e5b 100644 --- a/packages/form-js-viewer/src/render/components/form-fields/Textarea.js +++ b/packages/form-js-viewer/src/render/components/form-fields/Textarea.js @@ -38,7 +38,7 @@ export default function Textarea(props) { field, value: target.value }); - }, [ props.onChange ]); + }); const onInputBlur = () => { flushOnChange && flushOnChange(); diff --git a/packages/form-js-viewer/src/render/components/form-fields/Textfield.js b/packages/form-js-viewer/src/render/components/form-fields/Textfield.js index 0ad91ed4b..4e1b02185 100644 --- a/packages/form-js-viewer/src/render/components/form-fields/Textfield.js +++ b/packages/form-js-viewer/src/render/components/form-fields/Textfield.js @@ -42,7 +42,7 @@ export default function Textfield(props) { field, value: target.value }); - }, [ props.onChange ]); + }); const onInputBlur = () => { flushOnChange && flushOnChange(); diff --git a/packages/form-js-viewer/src/render/hooks/useCleanupMultiSelectValues.js b/packages/form-js-viewer/src/render/hooks/useCleanupMultiSelectValues.js index 0f65f5587..e23ea063a 100644 --- a/packages/form-js-viewer/src/render/hooks/useCleanupMultiSelectValues.js +++ b/packages/form-js-viewer/src/render/hooks/useCleanupMultiSelectValues.js @@ -10,10 +10,10 @@ export default function(props) { options, loadState, onChange, - values: valuesArray + values } = props; - const values = useDeepCompareState(valuesArray, []); + const memoizedValues = useDeepCompareState(values, []); // ensures that the values are always a subset of the possible options useEffect(() => { @@ -23,15 +23,15 @@ export default function(props) { } const optionValues = options.map(o => o.value); - const hasValuesNotInOptions = values.some(v => !hasEqualValue(v, optionValues)); + const hasValuesNotInOptions = memoizedValues.some(v => !hasEqualValue(v, optionValues)); if (hasValuesNotInOptions) { onChange({ field, - value: values.filter(v => hasEqualValue(v, optionValues)) + value: memoizedValues.filter(v => hasEqualValue(v, optionValues)) }); } - }, [ field, options, onChange, values, loadState ]); + }, [ field, options, onChange, memoizedValues, loadState ]); } \ No newline at end of file diff --git a/packages/form-js-viewer/src/render/hooks/useDeepCompareState.js b/packages/form-js-viewer/src/render/hooks/useDeepCompareState.js index 4cb30e943..9a60de252 100644 --- a/packages/form-js-viewer/src/render/hooks/useDeepCompareState.js +++ b/packages/form-js-viewer/src/render/hooks/useDeepCompareState.js @@ -17,7 +17,7 @@ export default function useDeepCompareState(value, defaultValue) { const [ state, setState ] = useState(defaultValue); - const previous = usePrevious(value, defaultValue, [ value ]); + const previous = usePrevious(value, defaultValue); const changed = !isEqual(previous, value); diff --git a/packages/form-js-viewer/src/render/hooks/useFlushDebounce.js b/packages/form-js-viewer/src/render/hooks/useFlushDebounce.js index cccaafafa..f2e7c7dc1 100644 --- a/packages/form-js-viewer/src/render/hooks/useFlushDebounce.js +++ b/packages/form-js-viewer/src/render/hooks/useFlushDebounce.js @@ -1,7 +1,7 @@ import { useCallback, useRef } from 'preact/hooks'; import useService from './useService'; -function useFlushDebounce(func, additionalDeps = []) { +function useFlushDebounce(func) { const timeoutRef = useRef(null); const lastArgsRef = useRef(null); @@ -29,7 +29,7 @@ function useFlushDebounce(func, additionalDeps = []) { lastArgsRef.current = null; }, delay); - }, [ func, delay, shouldDebounce, ...additionalDeps ]); + }, [ func, delay, shouldDebounce ]); const flushFunc = useCallback(() => { @@ -42,7 +42,7 @@ function useFlushDebounce(func, additionalDeps = []) { timeoutRef.current = null; } - }, [ func, ...additionalDeps ]); + }, [ func ]); return [ debounceFunc, flushFunc ]; } diff --git a/packages/form-js-viewer/src/render/hooks/usePrevious.js b/packages/form-js-viewer/src/render/hooks/usePrevious.js index f5c6d0766..21a3bfbf1 100644 --- a/packages/form-js-viewer/src/render/hooks/usePrevious.js +++ b/packages/form-js-viewer/src/render/hooks/usePrevious.js @@ -4,10 +4,10 @@ import { } from 'preact/hooks'; -export default function usePrevious(value, defaultValue, dependencies) { +export default function usePrevious(value, defaultValue = null) { const ref = useRef(defaultValue); - useEffect(() => ref.current = value, dependencies); + useEffect(() => ref.current = value, [ value ]); return ref.current; } \ No newline at end of file diff --git a/packages/form-js-viewer/test/helper/preactDebuggers.js b/packages/form-js-viewer/test/helper/preactDebuggers.js index 821261e74..cd81b95de 100644 --- a/packages/form-js-viewer/test/helper/preactDebuggers.js +++ b/packages/form-js-viewer/test/helper/preactDebuggers.js @@ -4,11 +4,11 @@ const usePrevious = (value, initialValue) => { const ref = useRef(initialValue); useEffect(() => { ref.current = value; - }); + }, [ value ]); return ref.current; }; -export function useEffectDebugger(effectHook, dependencies, dependencyNames = [], effectName = 'noname') { +export function useEffectDebugger(effect, dependencies, dependencyNames = [], effectName = 'noname') { const previousDeps = usePrevious(dependencies, []); const changedDeps = dependencies.reduce((accum, dependency, index) => { @@ -30,7 +30,7 @@ export function useEffectDebugger(effectHook, dependencies, dependencyNames = [] console.log('[use-effect-debugger] (' + effectName + ') ', changedDeps); } - useEffect(effectHook, dependencies); + useEffect(effect, [ effect, ...dependencies ]); } export function useCallbackDebugger(callback, dependencies, dependencyNames = [], callbackName = 'noname') { @@ -55,5 +55,5 @@ export function useCallbackDebugger(callback, dependencies, dependencyNames = [] console.log('[use-callback-debugger] (' + callbackName + ') ', changedDeps); } - return useCallback(callback, dependencies); + return useCallback(callback, [ callback, ...dependencies ]); } \ No newline at end of file