1818
1919import { EditorState } from "@codemirror/state" ;
2020import { EditorView , keymap , tooltips } from "@codemirror/view" ;
21- import React , { useEffect , useRef , useState } from "react" ;
21+ import React , { useEffect , useMemo , useRef , useState } from "react" ;
2222import { useFormContext } from "../../../../../context" ;
2323import {
2424 buildNeedTokenRefetchListner ,
@@ -88,8 +88,9 @@ export const ChipExpressionEditorComponent = (props: ChipExpressionEditorCompone
8888 const fieldContainerRef = useRef < HTMLDivElement > ( null ) ;
8989 const viewRef = useRef < EditorView | null > ( null ) ;
9090 const [ isTokenUpdateScheduled , setIsTokenUpdateScheduled ] = useState ( true ) ;
91- const completionsRef = useRef ( props . completions ) ;
91+ const completionsRef = useRef < CompletionItem [ ] > ( props . completions ) ;
9292 const helperPaneToggleButtonRef = useRef < HTMLButtonElement > ( null ) ;
93+ const completionsFetchScheduledRef = useRef < boolean > ( false ) ;
9394
9495 const { expressionEditor } = useFormContext ( ) ;
9596 const expressionEditorRpcManager = expressionEditor ?. rpcManager ;
@@ -99,6 +100,7 @@ export const ChipExpressionEditorComponent = (props: ChipExpressionEditorCompone
99100 } ) ;
100101
101102 const handleChangeListner = buildOnChangeListner ( ( newValue , cursor ) => {
103+ completionsFetchScheduledRef . current = true ;
102104 props . onChange ( newValue , cursor . position . to ) ;
103105 const textBeforeCursor = newValue . slice ( 0 , cursor . position . to ) ;
104106 const lastNonSpaceChar = textBeforeCursor . trimEnd ( ) . slice ( - 1 ) ;
@@ -124,7 +126,22 @@ export const ChipExpressionEditorComponent = (props: ChipExpressionEditorCompone
124126 setIsTokenUpdateScheduled ( true ) ;
125127 } ) ;
126128
127- const completionSource = buildCompletionSource ( ( ) => completionsRef . current ) ;
129+ const waitForStateChange = ( ) : Promise < CompletionItem [ ] > => {
130+ return new Promise ( ( resolve ) => {
131+ const checkState = ( ) => {
132+ if ( ! completionsFetchScheduledRef . current ) {
133+ resolve ( completionsRef . current ) ;
134+ } else {
135+ requestAnimationFrame ( checkState ) ;
136+ }
137+ } ;
138+ checkState ( ) ;
139+ } ) ;
140+ } ;
141+
142+ const completionSource = useMemo ( ( ) => {
143+ return buildCompletionSource ( waitForStateChange ) ;
144+ } , [ props . completions ] ) ;
128145
129146 const helperPaneKeymap = buildHelperPaneKeymap ( ( ) => helperPaneState . isOpen , ( ) => {
130147 setHelperPaneState ( prev => ( { ...prev , isOpen : false } ) ) ;
@@ -284,6 +301,7 @@ export const ChipExpressionEditorComponent = (props: ChipExpressionEditorCompone
284301 // just don't touch this.
285302 useEffect ( ( ) => {
286303 completionsRef . current = props . completions ;
304+ completionsFetchScheduledRef . current = false ;
287305 } , [ props . completions ] ) ;
288306
289307 useEffect ( ( ) => {
0 commit comments