11'use client' ;
22
3- import { getEmptyNode , getLocaleName , getNodeType } from '@intlayer/core' ;
3+ import {
4+ getContentNodeByKeyPath ,
5+ getEmptyNode ,
6+ getLocaleName ,
7+ getNodeType ,
8+ } from '@intlayer/core' ;
49import {
510 Button ,
611 KeyPathBreadcrumb ,
@@ -15,16 +20,15 @@ import {
1520 useInfiniteGetDictionaries ,
1621 useSearch ,
1722} from '@intlayer/design-system/hooks' ;
18- import { useConfiguration , useEditedContent } from '@intlayer/editor-react' ;
1923import {
20- type Dictionary ,
21- type KeyPath ,
22- type LocalesValues ,
23- NodeType ,
24- } from '@intlayer/types' ;
24+ useConfiguration ,
25+ useDictionariesRecordActions ,
26+ useEditedContent ,
27+ } from '@intlayer/editor-react' ;
28+ import { type Dictionary , type LocalesValues , NodeType } from '@intlayer/types' ;
2529import { Plus } from 'lucide-react' ;
2630import { useIntlayer , useLocale } from 'next-intlayer' ;
27- import { type FC , Suspense , useMemo , useState } from 'react' ;
31+ import { type FC , Suspense , useEffect , useMemo , useState } from 'react' ;
2832import { GroupedVirtuoso } from 'react-virtuoso' ;
2933import {
3034 type FlattenedDictionaryNode ,
@@ -36,16 +40,23 @@ const TranslateRow: FC<{
3640 node : FlattenedDictionaryNode ;
3741 selectedLocales : LocalesValues [ ] ;
3842} > = ( { node, selectedLocales } ) => {
39- const { dictionary, keyPath, content, nodeType } = node ;
40- const { addEditedContent } = useEditedContent ( ) ;
43+ const { dictionary, keyPath, content : originalContent , nodeType } = node ;
44+ const { editedContent , addEditedContent } = useEditedContent ( ) ;
4145 const configuration = useConfiguration ( ) ;
4246 const { defaultLocale } = configuration . internationalization ;
4347 const { addTranslation } = useIntlayer ( 'dictionary-list' ) ;
4448
49+ // Use edited content if available, otherwise fall back to original content from node
50+ const editedDictionaryContent = editedContent ?. [ dictionary . localId ! ] ?. content ;
51+ const content =
52+ typeof editedDictionaryContent === 'undefined'
53+ ? originalContent
54+ : getContentNodeByKeyPath ( editedDictionaryContent , keyPath ) ;
55+
4556 const isMultilingual =
4657 nodeType === NodeType . Translation ||
4758 ( nodeType === NodeType . Insertion &&
48- getNodeType ( ( content as any ) . content ) === NodeType . Translation ) ;
59+ getNodeType ( ( originalContent as any ) . content ) === NodeType . Translation ) ;
4960
5061 if ( isMultilingual ) {
5162 return (
@@ -81,16 +92,18 @@ const TranslateRow: FC<{
8192 contentMap [ Object . keys ( contentMap ) [ 0 ] ] ;
8293
8394 // Create an empty node based on the reference structure
84- const newContent = getEmptyNode ( referenceContent ) ;
85- const newKeyPath = [
86- ...keyPath ,
87- { type : nodeType , key : locale } ,
88- ] ;
95+ const newContent = {
96+ ...( ( editedContent as Record < string , any > ) ?? { } ) ,
97+ [ nodeType ] : {
98+ ...contentMap ,
99+ [ locale ] : getEmptyNode ( referenceContent ) ,
100+ } ,
101+ } ;
89102
90103 addEditedContent (
91104 dictionary . localId ! ,
92105 newContent ,
93- newKeyPath as KeyPath [ ]
106+ keyPath
94107 ) ;
95108 } }
96109 >
@@ -105,7 +118,9 @@ const TranslateRow: FC<{
105118 < TextEditor
106119 section = { translationContent }
107120 keyPath = { [ ...keyPath , { type : nodeType , key : locale } as any ] }
108- dictionary = { dictionary }
121+ dictionary = {
122+ editedContent ?. [ dictionary . localId ! ] ?? dictionary
123+ }
109124 />
110125 </ div >
111126 ) ;
@@ -141,20 +156,37 @@ const TranslateDashboardList: FC = () => {
141156 const { setSearch } = useSearch ( { } ) ;
142157 const { locale : currentLocale } = useLocale ( ) ;
143158 const [ search , setInternalSearch ] = useState ( '' ) ;
159+ const { setLocaleDictionaries } = useDictionariesRecordActions ( ) ?? { } ;
144160
145161 const { data, fetchNextPage, hasNextPage, isFetchingNextPage, isPending } =
146162 useInfiniteGetDictionaries ( { search, pageSize : 3 } ) ;
147163
148164 const { selectedLocales } = useLocaleSwitcherContent ( ) ;
149165
150- const allLoadedDictionaries : Record < string , Dictionary > = { } ;
151- data ?. pages . forEach ( ( page : any ) => {
152- ( page . data as Dictionary [ ] ) . forEach ( ( dict ) => {
153- if ( dict . localId ) {
154- allLoadedDictionaries [ dict . localId ] = dict ;
155- }
166+ const allLoadedDictionaries : Record < string , Dictionary > = useMemo ( ( ) => {
167+ const result : Record < string , Dictionary > = { } ;
168+ data ?. pages . forEach ( ( page : any ) => {
169+ ( page . data as Dictionary [ ] ) . forEach ( ( dict ) => {
170+ if ( dict . localId ) {
171+ result [ dict . localId ] = dict ;
172+ }
173+ } ) ;
156174 } ) ;
157- } ) ;
175+ return result ;
176+ } , [ data ?. pages ] ) ;
177+
178+ // Populate localeDictionaries context so addEditedContent can work properly
179+ useEffect ( ( ) => {
180+ if (
181+ setLocaleDictionaries &&
182+ Object . keys ( allLoadedDictionaries ) . length > 0
183+ ) {
184+ setLocaleDictionaries ( ( prev ) => ( {
185+ ...prev ,
186+ ...allLoadedDictionaries ,
187+ } ) ) ;
188+ }
189+ } , [ allLoadedDictionaries , setLocaleDictionaries ] ) ;
158190
159191 const flattenedNodes : FlattenedDictionaryNode [ ] =
160192 data ?. pages . flatMap ( ( page : any ) =>
0 commit comments