( lView: LView, index: number, parentTNode: TNode | null, subTemplateIndex: number, )
| 404 | } |
| 405 | |
| 406 | function prepareI18nBlockForHydrationImpl( |
| 407 | lView: LView, |
| 408 | index: number, |
| 409 | parentTNode: TNode | null, |
| 410 | subTemplateIndex: number, |
| 411 | ) { |
| 412 | const hydrationInfo = lView[HYDRATION]; |
| 413 | if (!hydrationInfo) { |
| 414 | return; |
| 415 | } |
| 416 | |
| 417 | if ( |
| 418 | !isI18nHydrationSupportEnabled() || |
| 419 | (parentTNode && |
| 420 | (isI18nInSkipHydrationBlock(parentTNode) || |
| 421 | isDisconnectedNode(hydrationInfo, parentTNode.index - HEADER_OFFSET))) |
| 422 | ) { |
| 423 | return; |
| 424 | } |
| 425 | |
| 426 | const tView = lView[TVIEW]; |
| 427 | const tI18n = tView.data[index] as TI18n; |
| 428 | ngDevMode && |
| 429 | assertDefined(tI18n, 'Expected i18n data to be present in a given TView slot during hydration'); |
| 430 | |
| 431 | function findHydrationRoot() { |
| 432 | if (isRootTemplateMessage(subTemplateIndex)) { |
| 433 | // This is the root of an i18n block. In this case, our hydration root will |
| 434 | // depend on where our parent TNode (i.e. the block with i18n applied) is |
| 435 | // in the DOM. |
| 436 | ngDevMode && assertDefined(parentTNode, 'Expected parent TNode while hydrating i18n root'); |
| 437 | const rootNode = locateNextRNode(hydrationInfo!, tView, lView, parentTNode!) as Node; |
| 438 | |
| 439 | // If this i18n block is attached to an <ng-container>, then we want to begin |
| 440 | // hydrating directly with the RNode. Otherwise, for a TNode with a physical DOM |
| 441 | // element, we want to recurse into the first child and begin there. |
| 442 | return parentTNode!.type & TNodeType.ElementContainer ? rootNode : rootNode.firstChild; |
| 443 | } |
| 444 | |
| 445 | // This is a nested template in an i18n block. In this case, the entire view |
| 446 | // is translated, and part of a dehydrated view in a container. This means that |
| 447 | // we can simply begin hydration with the first dehydrated child. |
| 448 | return hydrationInfo?.firstChild as Node; |
| 449 | } |
| 450 | |
| 451 | const currentNode = findHydrationRoot(); |
| 452 | ngDevMode && assertDefined(currentNode, 'Expected root i18n node during hydration'); |
| 453 | |
| 454 | const disconnectedNodes = initDisconnectedNodes(hydrationInfo) ?? new Set(); |
| 455 | const i18nNodes = (hydrationInfo.i18nNodes ??= new Map<number, RNode | null>()); |
| 456 | const caseQueue = hydrationInfo.data[I18N_DATA]?.[index - HEADER_OFFSET] ?? []; |
| 457 | const dehydratedIcuData = (hydrationInfo.dehydratedIcuData ??= new Map< |
| 458 | number, |
| 459 | DehydratedIcuData |
| 460 | >()); |
| 461 | |
| 462 | collectI18nNodesFromDom( |
| 463 | {hydrationInfo, lView, i18nNodes, disconnectedNodes, caseQueue, dehydratedIcuData}, |
nothing calls this directly
no test coverage detected
searching dependent graphs…