@@ -10,7 +10,15 @@ import {
1010 SpaceProps ,
1111 BorderProps
1212} from 'styled-system' ;
13- import { FC , PropsWithChildren } from 'react' ;
13+ import {
14+ FC ,
15+ PropsWithChildren ,
16+ RefAttributes ,
17+ useRef ,
18+ useState ,
19+ HTMLAttributes
20+ } from 'react' ;
21+ import useResizeObserver from 'use-resize-observer' ;
1422
1523const decoration = system ( { textDecoration : true } ) ;
1624type DecorationProps = Pick < CSSObject , 'textDecoration' > ;
@@ -113,6 +121,54 @@ ListItem.defaultProps = {
113121 margin : 0
114122} ;
115123
124+ const FitContainer = styled . div `
125+ width: 100%;
126+ display: flex;
127+ align-items: center;
128+ justify-content: center;
129+ ` ;
130+
131+ const ScalableText = styled (
132+ Text as FC < CommonTypographyProps & RefAttributes < HTMLDivElement > >
133+ ) < { scale : number } > `
134+ transform-origin: center;
135+ transform: scale(${ ( props ) => props . scale } );
136+ white-space: nowrap;
137+ ` ;
138+ ScalableText . defaultProps = {
139+ ...Text . defaultProps ,
140+ textAlign : 'center' ,
141+ scale : 1
142+ } ;
143+
144+ const FitText : FC <
145+ PropsWithChildren < CommonTypographyProps & HTMLAttributes < HTMLDivElement > >
146+ > = ( props ) => {
147+ const containerRef = useRef < HTMLDivElement > ( null ) ;
148+ const textRef = useRef < HTMLDivElement > ( null ) ;
149+ const [ scale , setScale ] = useState ( 1 ) ;
150+
151+ useResizeObserver ( {
152+ ref : containerRef ,
153+ onResize : ( ) => {
154+ if ( ! containerRef . current || ! textRef . current ) return ;
155+
156+ const containerWidth = containerRef . current . offsetWidth ;
157+ const textWidth = textRef . current . offsetWidth ;
158+ if ( textWidth === 0 ) return ;
159+
160+ const newScale = Math . min ( containerWidth / textWidth ) ;
161+ setScale ( newScale ) ;
162+ }
163+ } ) ;
164+
165+ return (
166+ < FitContainer ref = { containerRef } >
167+ < ScalableText { ...props } ref = { textRef } scale = { scale } />
168+ </ FitContainer >
169+ ) ;
170+ } ;
171+
116172export {
117173 Text ,
118174 Heading ,
@@ -121,5 +177,6 @@ export {
121177 UnorderedList ,
122178 ListItem ,
123179 Link ,
124- CodeSpan
180+ CodeSpan ,
181+ FitText
125182} ;
0 commit comments