88
99import type {
1010 LegendLayout ,
11+ MeasureTextFn ,
1112 ResolvedAnimation ,
1213 ResolvedChromeElement ,
1314 SankeyLayout ,
@@ -89,6 +90,7 @@ function renderChromeElement(
8990 element : ResolvedChromeElement ,
9091 className : string ,
9192 chromeKey : string ,
93+ measureText ?: MeasureTextFn ,
9294) : void {
9395 const text = createSVGElement ( 'text' ) ;
9496 setAttrs ( text , { x : element . x , y : element . y } ) ;
@@ -101,6 +103,7 @@ function renderChromeElement(
101103 element . style . fontSize ,
102104 element . style . fontWeight ,
103105 element . maxWidth ,
106+ measureText ,
104107 ) ;
105108
106109 if ( lines . length === 1 ) {
@@ -122,13 +125,13 @@ function renderChrome(parent: SVGElement, layout: SankeyLayout): void {
122125 const g = createSVGElement ( 'g' ) ;
123126 g . setAttribute ( 'class' , 'oc-chrome' ) ;
124127
125- const { chrome } = layout ;
128+ const { chrome, measureText } = layout ;
126129
127130 if ( chrome . title ) {
128- renderChromeElement ( g , chrome . title , 'oc-title' , 'title' ) ;
131+ renderChromeElement ( g , chrome . title , 'oc-title' , 'title' , measureText ) ;
129132 }
130133 if ( chrome . subtitle ) {
131- renderChromeElement ( g , chrome . subtitle , 'oc-subtitle' , 'subtitle' ) ;
134+ renderChromeElement ( g , chrome . subtitle , 'oc-subtitle' , 'subtitle' , measureText ) ;
132135 }
133136
134137 // Bottom chrome: positioned below the sankey drawing area.
@@ -140,6 +143,7 @@ function renderChrome(parent: SVGElement, layout: SankeyLayout): void {
140143 { ...chrome . source , y : bottomOffset + chrome . source . y } ,
141144 'oc-source' ,
142145 'source' ,
146+ measureText ,
143147 ) ;
144148 }
145149 if ( chrome . byline ) {
@@ -148,6 +152,7 @@ function renderChrome(parent: SVGElement, layout: SankeyLayout): void {
148152 { ...chrome . byline , y : bottomOffset + chrome . byline . y } ,
149153 'oc-byline' ,
150154 'byline' ,
155+ measureText ,
151156 ) ;
152157 }
153158 if ( chrome . footer ) {
@@ -156,6 +161,7 @@ function renderChrome(parent: SVGElement, layout: SankeyLayout): void {
156161 { ...chrome . footer , y : bottomOffset + chrome . footer . y } ,
157162 'oc-footer' ,
158163 'footer' ,
164+ measureText ,
159165 ) ;
160166 }
161167
@@ -476,7 +482,11 @@ function renderNodes(
476482// Labels rendering
477483// ---------------------------------------------------------------------------
478484
479- function renderLabels ( parent : SVGElement , nodes : SankeyNodeMark [ ] ) : void {
485+ function renderLabels (
486+ parent : SVGElement ,
487+ nodes : SankeyNodeMark [ ] ,
488+ measureText ?: MeasureTextFn ,
489+ ) : void {
480490 const g = createSVGElement ( 'g' ) ;
481491 g . setAttribute ( 'class' , 'oc-sankey-labels' ) ;
482492
@@ -492,7 +502,7 @@ function renderLabels(parent: SVGElement, nodes: SankeyNodeMark[]): void {
492502 if ( label . maxWidth !== undefined && label . maxWidth > 0 ) {
493503 const fontSize = label . style . fontSize ?? 12 ;
494504 const fontWeight = label . style . fontWeight ?? 400 ;
495- const lines = wrapText ( label . text , fontSize , fontWeight , label . maxWidth ) ;
505+ const lines = wrapText ( label . text , fontSize , fontWeight , label . maxWidth , measureText ) ;
496506 if ( lines . length > 1 ) {
497507 const lineHeight = fontSize * ( label . style . lineHeight ?? 1.3 ) ;
498508 // Center the multi-line block vertically around the label y position
@@ -585,7 +595,7 @@ export function renderSankeySVG(
585595 renderNodes ( svg , layout . nodes , animation ) ;
586596
587597 // Labels
588- renderLabels ( svg , layout . nodes ) ;
598+ renderLabels ( svg , layout . nodes , layout . measureText ) ;
589599
590600 // Legend
591601 renderLegend ( svg , layout . legend ) ;
0 commit comments