22import * as React from 'react'
33import emStyled , { CreateStyledComponent , CreateStyled } from '@emotion/styled'
44import { Theme } from '@emotion/react'
5- import { SystemProps } from '@xstyled/system'
5+ import { StyleGenerator , SystemProps , system } from '@xstyled/system'
66import { BoxElements } from '@xstyled/core'
7+ import { createShouldForwardProp } from './createShouldForwardProp'
78import { css } from './css'
8- import { x } from './x'
99
1010function flattenArgs ( arg : any , props : any ) : any {
1111 if ( typeof arg === 'function' ) return flattenArgs ( arg ( props ) , props )
1212 if ( Array . isArray ( arg ) ) return arg . map ( ( arg ) => flattenArgs ( arg , props ) )
1313 return arg
1414}
1515
16- function getCreateStyle ( baseCreateStyle : any ) {
16+ function getCreateStyle ( baseCreateStyle : any , ... generators : StyleGenerator [ ] ) {
1717 return ( strings : any , ...args : any ) =>
1818 baseCreateStyle ( ( props : any ) => {
19- const flattenedArgs = flattenArgs ( args , props )
20- // @ts -ignore
21- const result = css ( strings , ...flattenedArgs ) ( props )
22- return result
19+ let flattenedArgs = flattenArgs ( args , props )
20+
21+ // Emotion's css function can receive: template literal (array of
22+ // strings followed by interpolations), style object, or array of style
23+ // objects. Additional generators supplied to getCreateStyle need to be
24+ // interpolated differently depending on which form is called.
25+ if ( generators . length ) {
26+ if ( Array . isArray ( strings ) && typeof strings [ 0 ] === 'string' ) {
27+ // The tagged template literal should receive an equal number of
28+ // additional separators.
29+ strings = strings . concat ( generators . map ( ( ) => '\n' ) )
30+ flattenedArgs = flattenedArgs . concat ( flattenArgs ( generators , props ) )
31+ } else if ( Array . isArray ( strings ) ) {
32+ // Resolve generators to objects and append to existing array.
33+ strings = strings . concat ( flattenArgs ( generators , props ) )
34+ } else {
35+ // Convert single object to array.
36+ strings = [ strings ] . concat ( flattenArgs ( generators , props ) )
37+ }
38+ }
39+
40+ return css ( strings , ...flattenedArgs ) ( props )
2341 } )
2442}
2543
@@ -33,15 +51,25 @@ type BoxStyledTags = {
3351interface CreateXStyled extends CreateStyled , BoxStyledTags { }
3452
3553// @ts -ignore
36- export const styled : CreateXStyled = ( component : any , options : any ) => {
37- return getCreateStyle ( emStyled ( component , options ) )
38- }
54+ export const styled : CreateXStyled = ( component : any , options : any ) =>
55+ getCreateStyle ( emStyled ( component , options ) )
3956
40- styled . box = styled ( x . div )
57+ // exported for x.* but not for xstyled API
58+ // @ts -ignore
59+ export const styledWithGenerator : CreateXStyled = (
60+ component : any ,
61+ options : any ,
62+ generator : StyleGenerator ,
63+ ) => getCreateStyle ( emStyled ( component , options ) , generator )
64+
65+ const shouldForwardProp = createShouldForwardProp ( system )
66+
67+ // @ts -ignore
68+ styled . box = styledWithGenerator ( 'div' , { shouldForwardProp } , system )
4169
4270Object . keys ( emStyled ) . forEach ( ( key ) => {
4371 // @ts -ignore
4472 styled [ key ] = styled ( key )
4573 // @ts -ignore
46- styled [ `${ key } Box` ] = styled ( x [ key ] )
74+ styled [ `${ key } Box` ] = styledWithGenerator ( key , { shouldForwardProp } , system )
4775} )
0 commit comments