UNPKG

@lexical/react

Version:

This package provides Lexical components and hooks for React applications.

70 lines (60 loc) • 2.3 kB
/** * Copyright (c) Meta Platforms, Inc. and affiliates. * * This source code is licensed under the MIT license found in the * LICENSE file in the root directory of this source tree. * */ import { useLexicalComposerContext } from '@lexical/react/LexicalComposerContext'; import { useLayoutEffect, useEffect, useMemo, useState, useRef } from 'react'; import { CAN_USE_DOM } from 'lexical'; /** * Copyright (c) Meta Platforms, Inc. and affiliates. * * This source code is licensed under the MIT license found in the * LICENSE file in the root directory of this source tree. * */ // This workaround is no longer necessary in React 19, // but we currently support React >=18.x // https://github.com/facebook/react/pull/26395 const useLayoutEffectImpl = CAN_USE_DOM ? useLayoutEffect : useEffect; /** * Copyright (c) Meta Platforms, Inc. and affiliates. * * This source code is licensed under the MIT license found in the * LICENSE file in the root directory of this source tree. * */ /** * Describes how {@link useLexicalSubscription} reads a value from the editor: an * `initialValueFn` that computes the current value, and a `subscribe` function * that registers a listener for changes and returns an unsubscribe callback. */ /** * Shortcut to Lexical subscriptions when values are used for render. * @param subscription - The function to create the {@link LexicalSubscription}. This function's identity must be stable (e.g. defined at module scope or with useCallback). */ function useLexicalSubscription(subscription) { const [editor] = useLexicalComposerContext(); const initializedSubscription = useMemo(() => subscription(editor), [editor, subscription]); const [value, setValue] = useState(() => initializedSubscription.initialValueFn()); const valueRef = useRef(value); useLayoutEffectImpl(() => { const { initialValueFn, subscribe } = initializedSubscription; const currentValue = initialValueFn(); if (valueRef.current !== currentValue) { valueRef.current = currentValue; setValue(currentValue); } return subscribe(newValue => { valueRef.current = newValue; setValue(newValue); }); }, [initializedSubscription, subscription]); return value; } export { useLexicalSubscription };