@tamagui/core 1.0.1-beta.193 → 1.0.1-beta.194

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (220) hide show
  1. package/dist/cjs/Tamagui.js +4 -2
  2. package/dist/cjs/Tamagui.js.map +2 -2
  3. package/dist/cjs/config.js +1 -2
  4. package/dist/cjs/config.js.map +2 -2
  5. package/dist/cjs/constants/constants.js +13 -8
  6. package/dist/cjs/constants/constants.js.map +2 -2
  7. package/dist/cjs/contexts/TextAncestorContext.js +3 -16
  8. package/dist/cjs/contexts/TextAncestorContext.js.map +3 -3
  9. package/dist/cjs/createComponent.js +194 -289
  10. package/dist/cjs/createComponent.js.map +2 -2
  11. package/dist/cjs/createTamagui.js +15 -16
  12. package/dist/cjs/createTamagui.js.map +3 -3
  13. package/dist/cjs/createVariable.js +1 -2
  14. package/dist/cjs/createVariable.js.map +2 -2
  15. package/dist/cjs/helpers/ThemeManager.js +7 -14
  16. package/dist/cjs/helpers/ThemeManager.js.map +2 -2
  17. package/dist/cjs/helpers/{createShallowUpdate.js → cache.js} +20 -21
  18. package/dist/cjs/helpers/cache.js.map +7 -0
  19. package/dist/cjs/helpers/createMediaStyle.js +14 -8
  20. package/dist/cjs/helpers/createMediaStyle.js.map +2 -2
  21. package/dist/cjs/helpers/extendStaticConfig.js +0 -1
  22. package/dist/cjs/helpers/extendStaticConfig.js.map +2 -2
  23. package/dist/cjs/helpers/getSplitStyles.js +212 -93
  24. package/dist/cjs/helpers/getSplitStyles.js.map +3 -3
  25. package/dist/cjs/helpers/getStylesAtomic.js +16 -36
  26. package/dist/cjs/helpers/getStylesAtomic.js.map +3 -3
  27. package/dist/cjs/helpers/insertStyleRule.js +14 -6
  28. package/dist/cjs/helpers/insertStyleRule.js.map +2 -2
  29. package/dist/cjs/helpers/matchMedia.js.map +2 -2
  30. package/dist/cjs/helpers/mergeTransform.js.map +1 -1
  31. package/dist/cjs/helpers/normalizeValueWithProperty.js +32 -2
  32. package/dist/cjs/helpers/normalizeValueWithProperty.js.map +2 -2
  33. package/dist/cjs/helpers/useShallowSetState.js.map +2 -2
  34. package/dist/cjs/hooks/getThemeUnwrapped.js +1 -3
  35. package/dist/cjs/hooks/getThemeUnwrapped.js.map +2 -2
  36. package/dist/cjs/hooks/useElementLayout.js +92 -0
  37. package/dist/cjs/hooks/useElementLayout.js.map +7 -0
  38. package/dist/cjs/hooks/useIsTouchDevice.js +2 -10
  39. package/dist/cjs/hooks/useIsTouchDevice.js.map +2 -2
  40. package/dist/cjs/hooks/useMedia.js +77 -84
  41. package/dist/cjs/hooks/useMedia.js.map +2 -2
  42. package/dist/cjs/hooks/useMedia.test.js +2 -0
  43. package/dist/cjs/{helpers/validate.js.map → hooks/useMedia.test.js.map} +0 -0
  44. package/dist/cjs/hooks/usePressablePressResponder.js +370 -0
  45. package/dist/cjs/hooks/usePressablePressResponder.js.map +7 -0
  46. package/dist/cjs/hooks/useSafeRef.js +13 -15
  47. package/dist/cjs/hooks/useSafeRef.js.map +2 -2
  48. package/dist/cjs/hooks/useTheme.js +3 -4
  49. package/dist/cjs/hooks/useTheme.js.map +2 -2
  50. package/dist/cjs/index.js +1 -17
  51. package/dist/cjs/index.js.map +2 -2
  52. package/dist/cjs/static.js +0 -20
  53. package/dist/cjs/static.js.map +2 -2
  54. package/dist/cjs/styled.js +4 -22
  55. package/dist/cjs/styled.js.map +2 -2
  56. package/dist/cjs/types.js.map +1 -1
  57. package/dist/cjs/{hooks/useIsSSR.js → views/AbsoluteFill.js} +18 -23
  58. package/dist/cjs/views/AbsoluteFill.js.map +7 -0
  59. package/dist/cjs/views/AbsoluteFill.native.js +45 -0
  60. package/dist/cjs/views/AbsoluteFill.native.js.map +7 -0
  61. package/dist/cjs/views/FontLanguage.native.js.map +2 -2
  62. package/dist/cjs/views/Stack.js.map +1 -1
  63. package/dist/cjs/views/TamaguiProvider.js +3 -2
  64. package/dist/cjs/views/TamaguiProvider.js.map +2 -2
  65. package/dist/cjs/views/Text.js.map +1 -1
  66. package/dist/cjs/views/ThemeReset.js +10 -10
  67. package/dist/cjs/views/ThemeReset.js.map +2 -2
  68. package/dist/esm/Tamagui.js +4 -2
  69. package/dist/esm/Tamagui.js.map +2 -2
  70. package/dist/esm/config.js +1 -2
  71. package/dist/esm/config.js.map +2 -2
  72. package/dist/esm/constants/constants.js +11 -7
  73. package/dist/esm/constants/constants.js.map +2 -2
  74. package/dist/esm/contexts/TextAncestorContext.js +2 -13
  75. package/dist/esm/contexts/TextAncestorContext.js.map +2 -2
  76. package/dist/esm/createComponent.js +193 -291
  77. package/dist/esm/createComponent.js.map +2 -2
  78. package/dist/esm/createTamagui.js +15 -16
  79. package/dist/esm/createTamagui.js.map +3 -3
  80. package/dist/esm/createVariable.js +1 -2
  81. package/dist/esm/createVariable.js.map +2 -2
  82. package/dist/esm/helpers/ThemeManager.js +7 -14
  83. package/dist/esm/helpers/ThemeManager.js.map +2 -2
  84. package/dist/esm/helpers/cache.js +18 -0
  85. package/dist/esm/helpers/cache.js.map +7 -0
  86. package/dist/esm/helpers/createMediaStyle.js +14 -8
  87. package/dist/esm/helpers/createMediaStyle.js.map +2 -2
  88. package/dist/esm/helpers/extendStaticConfig.js +0 -1
  89. package/dist/esm/helpers/extendStaticConfig.js.map +2 -2
  90. package/dist/esm/helpers/getSplitStyles.js +221 -94
  91. package/dist/esm/helpers/getSplitStyles.js.map +3 -3
  92. package/dist/esm/helpers/getStylesAtomic.js +13 -26
  93. package/dist/esm/helpers/getStylesAtomic.js.map +2 -2
  94. package/dist/esm/helpers/insertStyleRule.js +14 -6
  95. package/dist/esm/helpers/insertStyleRule.js.map +2 -2
  96. package/dist/esm/helpers/matchMedia.js.map +2 -2
  97. package/dist/esm/helpers/mergeTransform.js.map +1 -1
  98. package/dist/esm/helpers/normalizeValueWithProperty.js +30 -1
  99. package/dist/esm/helpers/normalizeValueWithProperty.js.map +2 -2
  100. package/dist/esm/helpers/useShallowSetState.js.map +2 -2
  101. package/dist/esm/hooks/getThemeUnwrapped.js +1 -3
  102. package/dist/esm/hooks/getThemeUnwrapped.js.map +2 -2
  103. package/dist/esm/hooks/useElementLayout.js +66 -0
  104. package/dist/esm/hooks/useElementLayout.js.map +7 -0
  105. package/dist/esm/hooks/useIsTouchDevice.js +3 -11
  106. package/dist/esm/hooks/useIsTouchDevice.js.map +2 -2
  107. package/dist/esm/hooks/useMedia.js +74 -83
  108. package/dist/esm/hooks/useMedia.js.map +2 -2
  109. package/dist/esm/hooks/useMedia.test.js +1 -0
  110. package/dist/esm/{helpers/validate.js.map → hooks/useMedia.test.js.map} +0 -0
  111. package/dist/esm/hooks/usePressablePressResponder.js +346 -0
  112. package/dist/esm/hooks/usePressablePressResponder.js.map +7 -0
  113. package/dist/esm/hooks/useSafeRef.js +13 -15
  114. package/dist/esm/hooks/useSafeRef.js.map +2 -2
  115. package/dist/esm/hooks/useTheme.js +3 -4
  116. package/dist/esm/hooks/useTheme.js.map +2 -2
  117. package/dist/esm/index.js +1 -14
  118. package/dist/esm/index.js.map +2 -2
  119. package/dist/esm/static.js +0 -14
  120. package/dist/esm/static.js.map +2 -2
  121. package/dist/esm/styled.js +4 -22
  122. package/dist/esm/styled.js.map +2 -2
  123. package/dist/esm/views/AbsoluteFill.js +17 -0
  124. package/dist/esm/views/AbsoluteFill.js.map +7 -0
  125. package/dist/esm/views/AbsoluteFill.native.js +21 -0
  126. package/dist/esm/views/AbsoluteFill.native.js.map +7 -0
  127. package/dist/esm/views/FontLanguage.native.js.map +2 -2
  128. package/dist/esm/views/Stack.js.map +1 -1
  129. package/dist/esm/views/TamaguiProvider.js +5 -4
  130. package/dist/esm/views/TamaguiProvider.js.map +2 -2
  131. package/dist/esm/views/Text.js.map +1 -1
  132. package/dist/esm/views/ThemeReset.js +10 -10
  133. package/dist/esm/views/ThemeReset.js.map +2 -2
  134. package/package.json +14 -14
  135. package/src/Tamagui.ts +7 -3
  136. package/src/config.ts +2 -3
  137. package/src/constants/constants.ts +10 -6
  138. package/src/contexts/TextAncestorContext.tsx +1 -8
  139. package/src/createComponent.tsx +248 -418
  140. package/src/createTamagui.ts +16 -19
  141. package/src/createVariable.ts +1 -3
  142. package/src/helpers/ThemeManager.tsx +7 -15
  143. package/src/helpers/cache.ts +18 -0
  144. package/src/helpers/createMediaStyle.ts +16 -9
  145. package/src/helpers/extendStaticConfig.ts +0 -1
  146. package/src/helpers/getSplitStyles.tsx +257 -151
  147. package/src/helpers/getStylesAtomic.ts +14 -34
  148. package/src/helpers/insertStyleRule.tsx +16 -8
  149. package/src/helpers/matchMedia.ts +1 -0
  150. package/src/helpers/mergeTransform.ts +1 -1
  151. package/src/helpers/normalizeValueWithProperty.ts +30 -0
  152. package/src/helpers/useShallowSetState.tsx +0 -1
  153. package/src/hooks/getThemeUnwrapped.tsx +1 -2
  154. package/src/hooks/useElementLayout.tsx +90 -0
  155. package/src/hooks/useIsTouchDevice.tsx +3 -17
  156. package/src/hooks/useMedia.tsx +80 -87
  157. package/src/hooks/useSafeRef.ts +17 -18
  158. package/src/hooks/useTheme.tsx +4 -4
  159. package/src/index.ts +1 -11
  160. package/src/static.ts +0 -10
  161. package/src/styled.tsx +15 -33
  162. package/src/types.tsx +58 -55
  163. package/src/views/FontLanguage.native.tsx +1 -0
  164. package/src/views/Stack.tsx +1 -1
  165. package/src/views/TamaguiProvider.tsx +5 -5
  166. package/src/views/Text.tsx +1 -1
  167. package/src/views/ThemeReset.tsx +11 -11
  168. package/types/Tamagui.d.ts +6 -4
  169. package/types/constants/constants.d.ts +14 -3
  170. package/types/contexts/TextAncestorContext.d.ts +1 -3
  171. package/types/createComponent.d.ts +0 -15
  172. package/types/helpers/ThemeManager.d.ts +2 -3
  173. package/types/helpers/cache.d.ts +12 -0
  174. package/types/helpers/calc.d.ts +0 -16
  175. package/types/helpers/createMediaStyle.d.ts +1 -1
  176. package/types/helpers/getSplitStyles.d.ts +6 -10
  177. package/types/helpers/getStylesAtomic.d.ts +1 -5
  178. package/types/helpers/insertStyleRule.d.ts +2 -2
  179. package/types/helpers/mergeTransform.d.ts +1 -1
  180. package/types/helpers/normalizeValueWithProperty.d.ts +1 -0
  181. package/types/hooks/useElementLayout.d.ts +27 -0
  182. package/types/hooks/useMedia.d.ts +3 -1
  183. package/types/hooks/useMedia.test.d.ts +1 -0
  184. package/types/hooks/usePressablePressResponder.d.ts +84 -0
  185. package/types/index.d.ts +1 -11
  186. package/types/static.d.ts +0 -1
  187. package/types/types.d.ts +42 -44
  188. package/types/views/AbsoluteFill.d.ts +5 -0
  189. package/types/views/AbsoluteFill.native.d.ts +3 -0
  190. package/types/views/Stack.d.ts +1 -1
  191. package/types/views/Text.d.ts +1 -1
  192. package/dist/cjs/constants/platform.js +0 -74
  193. package/dist/cjs/constants/platform.js.map +0 -7
  194. package/dist/cjs/constants/platform.native.js +0 -62
  195. package/dist/cjs/constants/platform.native.js.map +0 -7
  196. package/dist/cjs/helpers/createShallowUpdate.js.map +0 -7
  197. package/dist/cjs/helpers/validate.js +0 -2
  198. package/dist/cjs/hooks/useDidFinishSSR.js +0 -60
  199. package/dist/cjs/hooks/useDidFinishSSR.js.map +0 -7
  200. package/dist/cjs/hooks/useIsSSR.js.map +0 -7
  201. package/dist/esm/constants/platform.js +0 -39
  202. package/dist/esm/constants/platform.js.map +0 -7
  203. package/dist/esm/constants/platform.native.js +0 -28
  204. package/dist/esm/constants/platform.native.js.map +0 -7
  205. package/dist/esm/helpers/createShallowUpdate.js +0 -20
  206. package/dist/esm/helpers/createShallowUpdate.js.map +0 -7
  207. package/dist/esm/helpers/validate.js +0 -1
  208. package/dist/esm/hooks/useDidFinishSSR.js +0 -35
  209. package/dist/esm/hooks/useDidFinishSSR.js.map +0 -7
  210. package/dist/esm/hooks/useIsSSR.js +0 -22
  211. package/dist/esm/hooks/useIsSSR.js.map +0 -7
  212. package/src/helpers/assignNativePropsToWeb.tsx +0 -178
  213. package/src/helpers/calc.ts +0 -68
  214. package/src/helpers/getFont.tsx +0 -43
  215. package/src/helpers/getStackSize.ts +0 -22
  216. package/src/helpers/startTransition.ts +0 -4
  217. package/src/hooks/useConstant.tsx +0 -19
  218. package/src/hooks/useIsMounted.ts +0 -16
  219. package/src/hooks/usePressable.tsx +0 -9
  220. package/src/hooks/useUnmountEffect.ts +0 -5
@@ -1,3 +1,4 @@
1
+ import { useComposedRefs } from '@tamagui/compose-refs'
1
2
  import { isClient, isRSC, isWeb, useIsomorphicLayoutEffect } from '@tamagui/constants'
2
3
  /* eslint-disable react-hooks/rules-of-hooks */
3
4
  import {
@@ -6,16 +7,13 @@ import {
6
7
  validPseudoKeys,
7
8
  validStyles,
8
9
  } from '@tamagui/helpers'
9
- import {
10
- useElementLayout,
11
- useMergeRefs,
12
- usePlatformMethods,
13
- useResponderEvents,
14
- } from '@tamagui/rnw'
10
+ import { useResponderEvents } from '@tamagui/react-native-use-responder-events'
11
+ import type { ViewStyle } from '@tamagui/types-react-native'
15
12
  import { useForceUpdate } from '@tamagui/use-force-update'
16
13
  import React, {
17
14
  Children,
18
15
  Fragment,
16
+ RefObject,
19
17
  createElement,
20
18
  forwardRef,
21
19
  memo,
@@ -23,13 +21,11 @@ import React, {
23
21
  useContext,
24
22
  useEffect,
25
23
  } from 'react'
26
- import { Text, View, ViewStyle } from 'react-native'
27
24
 
28
- import { getConfig, onConfiguredOnce } from './config'
25
+ import { onConfiguredOnce } from './config'
29
26
  import { stackDefaultStyles } from './constants/constants'
30
27
  import { FontLanguageContext } from './contexts/FontLanguageContext'
31
28
  import { TextAncestorContext } from './contexts/TextAncestorContext'
32
- import { assignNativePropsToWeb } from './helpers/assignNativePropsToWeb'
33
29
  import { getReturnVariablesAs } from './helpers/createPropMapper'
34
30
  import { extendStaticConfig, parseStaticConfig } from './helpers/extendStaticConfig'
35
31
  import {
@@ -42,8 +38,8 @@ import { getAllSelectors } from './helpers/insertStyleRule'
42
38
  import { mergeProps } from './helpers/mergeProps'
43
39
  import { proxyThemeVariables } from './helpers/proxyThemeVariables'
44
40
  import { useShallowSetState } from './helpers/useShallowSetState'
41
+ import { getRect, measureLayout, useElementLayout } from './hooks/useElementLayout'
45
42
  import { addMediaQueryListener, getInitialMediaState } from './hooks/useMedia'
46
- import { usePressable } from './hooks/usePressable'
47
43
  import { useServerRef, useServerState } from './hooks/useServerHooks'
48
44
  import { getThemeManager, useTheme } from './hooks/useTheme'
49
45
  import {
@@ -63,11 +59,20 @@ import {
63
59
  } from './types'
64
60
  import { usePressability } from './vendor/Pressability'
65
61
  import { Slot, mergeEvent } from './views/Slot'
62
+ import { Stack } from './views/Stack'
66
63
  import { wrapThemeManagerContext } from './views/Theme'
67
64
 
68
65
  React['keep']
69
66
 
67
+ /**
68
+ * All things that need one-time setup after createTamagui is called
69
+ */
70
70
  let defaultComponentState: TamaguiComponentState | null = null
71
+ let defaultComponentStateMounted: TamaguiComponentState | null = null
72
+ let tamaguiConfig: TamaguiInternalConfig
73
+ let AnimatedText: any
74
+ let AnimatedView: any
75
+ let initialTheme: any
71
76
 
72
77
  export const mouseUps = new Set<Function>()
73
78
  if (typeof document !== 'undefined') {
@@ -88,8 +93,17 @@ function mergeShorthands({ defaultProps }: StaticConfigParsed, { shorthands }: T
88
93
  }
89
94
  }
90
95
 
91
- let initialTheme: any
92
- let config: TamaguiInternalConfig
96
+ /**
97
+ * Only on native do we need the actual underlying View/Text
98
+ * On the web we avoid react-native altogether in core.
99
+ */
100
+ let BaseText: any
101
+ let BaseView: any
102
+ if (process.env.TAMAGUI_TARGET === 'native') {
103
+ const native = require('react-native')
104
+ BaseText = native.Text || native.default.Text
105
+ BaseView = native.View || native.default.View
106
+ }
93
107
 
94
108
  export function createComponent<
95
109
  ComponentPropTypes extends Object = {},
@@ -106,10 +120,7 @@ export function createComponent<
106
120
  })()
107
121
 
108
122
  const defaultComponentClassName = `is_${staticConfig.componentName}`
109
- let tamaguiConfig: TamaguiInternalConfig
110
- let AnimatedText: any
111
- let AnimatedView: any
112
- let avoidClassesWhileAnimating = true
123
+ const avoidClassesWhileAnimating = true
113
124
  let defaultNativeStyle: any
114
125
  let tamaguiDefaultProps: any
115
126
  let initialSplitStyles: SplitStyleResult
@@ -126,7 +137,6 @@ export function createComponent<
126
137
  }
127
138
 
128
139
  const debugProp = props['debug']
129
-
130
140
  const { Component, isText, isZStack } = staticConfig
131
141
  const componentName = props.componentName || staticConfig.componentName
132
142
  const componentClassName = props.asChild
@@ -136,14 +146,39 @@ export function createComponent<
136
146
  : defaultComponentClassName
137
147
 
138
148
  const forceUpdate = useForceUpdate()
139
- config = config || getConfig()
140
149
  const theme = useTheme(props.theme, componentName, props, forceUpdate)
141
150
 
142
- const states = useServerState<TamaguiComponentState>(defaultComponentState!)
151
+ /**
152
+ * Component state for tracking animations, pseudos
153
+ */
154
+ const hasEnterStyle = !!props.enterStyle
155
+ const needsMount = Boolean((isWeb ? isClient : true) && (hasEnterStyle || props.animation))
156
+ const states = useServerState<TamaguiComponentState>(
157
+ needsMount ? defaultComponentState! : defaultComponentStateMounted!
158
+ )
159
+
143
160
  const state = propsIn.forceStyle ? { ...states[0], [propsIn.forceStyle]: true } : states[0]
161
+ const setState = states[1]
162
+ const setStateShallow = useShallowSetState(setState)
163
+
164
+ const shouldSetMounted = needsMount && !state.mounted
165
+ const setMounted = shouldSetMounted
166
+ ? () => {
167
+ // for some reason without some small delay it doesn't animate css
168
+ setTimeout(
169
+ () => {
170
+ setStateShallow({
171
+ mounted: true,
172
+ })
173
+ },
174
+ isWeb ? 10 : 0
175
+ )
176
+ }
177
+ : undefined
144
178
 
145
179
  const shouldAvoidClasses =
146
180
  !!(props.animation && avoidClassesWhileAnimating) || !staticConfig.acceptsClassName
181
+
147
182
  const shouldForcePseudo = !!propsIn.forceStyle
148
183
  const hasTextAncestor = !!(isWeb && isText ? useContext(TextAncestorContext) : false)
149
184
  const splitStyleState =
@@ -163,19 +198,45 @@ export function createComponent<
163
198
 
164
199
  const languageContext = isRSC ? null : useContext(FontLanguageContext)
165
200
 
201
+ const useAnimations = tamaguiConfig.animations?.useAnimations as UseAnimationHook | undefined
202
+ const nextIsAnimated = !!(useAnimations && props.animation)
203
+ // conditional but if ever true stays true
204
+ const isAnimated = nextIsAnimated || state.hasAnimation
205
+ if (nextIsAnimated && !state.hasAnimation) {
206
+ setStateShallow({ hasAnimation: true })
207
+ }
208
+
209
+ const isTaggable = !Component || typeof Component === 'string'
210
+ // default to tag, fallback to component (when both strings)
211
+ const element = isWeb ? (isTaggable ? props.tag || Component : Component) : Component
212
+
213
+ const BaseTextComponent = BaseText || element || 'span'
214
+ const BaseViewComponent = BaseView || element || (hasTextAncestor ? 'span' : 'div')
215
+ let elementType = isText
216
+ ? (isAnimated ? AnimatedText : null) || BaseTextComponent
217
+ : (isAnimated ? AnimatedView : null) || BaseViewComponent
218
+
219
+ elementType = Component || elementType
220
+ const isStringElement = typeof elementType === 'string'
221
+
166
222
  const splitStyles = useSplitStyles(
167
223
  props,
168
224
  staticConfig,
169
225
  theme,
170
226
  splitStyleState,
171
- props.asChild ? null : initialSplitStyles?.classNames,
227
+ props.asChild ? null : initialSplitStyles,
172
228
  languageContext || undefined,
229
+ elementType,
173
230
  debugProp
174
231
  )
175
232
 
176
233
  const hostRef = useServerRef<TamaguiElement>(null)
177
- const setState = states[1]
178
- const setStateShallow = useShallowSetState(setState)
234
+
235
+ // animation setup
236
+ const isReactNativeWeb = Boolean(
237
+ staticConfig.isReactNativeWeb || (isAnimated && tamaguiConfig.animations.isReactNativeWeb)
238
+ )
239
+ const isAnimatedReactNativeWeb = isAnimated && avoidClassesWhileAnimating
179
240
 
180
241
  if (process.env.NODE_ENV === 'development') {
181
242
  if (!process.env.TAMAGUI_TARGET) {
@@ -187,7 +248,7 @@ export function createComponent<
187
248
  const name = `${
188
249
  componentName || Component?.displayName || Component?.name || '[Unnamed Component]'
189
250
  }`
190
- const type = staticConfig.isReactNativeWeb ? 'rnw' : 'tamagui'
251
+ const type = isReactNativeWeb ? 'rnw' : 'tamagui'
191
252
  const banner = `${name} ${propsIn['data-is'] || ''} ${type}`
192
253
  // eslint-disable-next-line no-console
193
254
  console.group(`%c 🐛 ${banner}`, 'background: yellow;')
@@ -221,55 +282,16 @@ export function createComponent<
221
282
  mediaKeys,
222
283
  } = splitStyles
223
284
 
224
- // media queries
225
- useIsomorphicLayoutEffect(() => {
226
- if (!mediaKeys.length) {
227
- return
228
- }
229
- const disposers: any[] = []
230
- for (const key of mediaKeys) {
231
- disposers.push(
232
- addMediaQueryListener(key, (next: boolean) => {
233
- setState((prev) => {
234
- if (prev.mediaState![key] !== next) {
235
- return {
236
- ...prev,
237
- mediaState: {
238
- ...prev.mediaState,
239
- [key]: next,
240
- },
241
- }
242
- }
243
- return prev
244
- })
245
- })
246
- )
247
- }
248
- return () => {}
249
- }, [mediaKeys.join(',')])
250
-
251
- // animations
252
- const useAnimations = tamaguiConfig?.animations?.useAnimations as UseAnimationHook | undefined
253
-
254
- const nextIsAnimated = !!(useAnimations && props.animation)
255
- // conditional but if ever true stays true
256
- const isAnimated = nextIsAnimated || state.hasAnimation
257
- if (nextIsAnimated && !state.hasAnimation) {
258
- setStateShallow({ hasAnimation: true })
259
- }
260
-
261
285
  const animationFeatureStylesIn = props.animation
262
286
  ? { ...defaultNativeStyle, ...splitStylesStyle }
263
287
  : null
264
288
  const propsWithAnimation = props as UseAnimationProps
265
289
 
266
- // lets make changing the key mandatory for adding/removing animations
267
- // reason is animations are heavy no way around it, and must be run inline here (🙅 loading as a sub-component)
268
- // because they need to sync update on first render. it's pretty rare too going to/from no animation => animation
269
- // so requiring key change on animation change is least-bad option.
270
- // plus, React use() may let us get away with conditional hooks soon :)
290
+ // once you set animation prop don't remove it, you can set to undefined/false
291
+ // reason is animations are heavy - no way around it, and must be run inline here (🙅 loading as a sub-component)
292
+ let animationStyles: any
271
293
  if (!isRSC && isAnimated && useAnimations) {
272
- const animationState = useAnimations(propsWithAnimation, {
294
+ const animations = useAnimations(propsWithAnimation, {
273
295
  state,
274
296
  pseudos,
275
297
  onDidAnimate: props.onDidAnimate,
@@ -321,7 +343,6 @@ export function createComponent<
321
343
  // enterStyle,
322
344
  pseudos.hoverStyle,
323
345
  pseudos.focusStyle,
324
- pseudos.pressStyle,
325
346
  pseudos.pressStyle
326
347
  )
327
348
 
@@ -332,7 +353,7 @@ export function createComponent<
332
353
  exitStyle && isExiting && merge(style, exitStyle)
333
354
 
334
355
  if (process.env.NODE_ENV === 'development') {
335
- if (debugProp) {
356
+ if (debugProp === 'verbose') {
336
357
  // eslint-disable-next-line no-console
337
358
  console.log('animation style', style)
338
359
  }
@@ -343,16 +364,41 @@ export function createComponent<
343
364
  //, delay
344
365
  })
345
366
 
346
- // must be properly memoized
347
- if (animationState !== state.animation) {
348
- setStateShallow({
349
- animation: animationState,
350
- })
367
+ if (animations) {
368
+ animationStyles = animations.style
351
369
  }
352
370
  }
353
371
 
372
+ // media queries
373
+ useIsomorphicLayoutEffect(() => {
374
+ if (!mediaKeys.length) return
375
+ const disposers: any[] = []
376
+ for (const key of mediaKeys) {
377
+ disposers.push(
378
+ addMediaQueryListener(key, (next: boolean) => {
379
+ setState((prev) => {
380
+ if (prev.mediaState![key] !== next) {
381
+ return {
382
+ ...prev,
383
+ mediaState: {
384
+ ...prev.mediaState,
385
+ [key]: next,
386
+ },
387
+ }
388
+ }
389
+ return prev
390
+ })
391
+ })
392
+ )
393
+ }
394
+ return () => {
395
+ for (const disposer of disposers) {
396
+ disposer()
397
+ }
398
+ }
399
+ }, [mediaKeys.join(',')])
400
+
354
401
  const {
355
- tag,
356
402
  hitSlop,
357
403
  asChild,
358
404
  children,
@@ -382,20 +428,6 @@ export function createComponent<
382
428
  ...nonTamaguiProps
383
429
  } = viewPropsIn
384
430
 
385
- // get the right component
386
- const isTaggable = !Component || typeof Component === 'string'
387
-
388
- // default to tag, fallback to component (when both strings)
389
- const element = isWeb ? (isTaggable ? tag || Component : Component) : Component
390
- const BaseTextComponent = !isWeb ? Text : element || 'span'
391
- const BaseViewComponent = !isWeb ? View : element || (hasTextAncestor ? 'span' : 'div')
392
- let elementType = isText
393
- ? (isAnimated ? AnimatedText || Text : null) || BaseTextComponent
394
- : (isAnimated ? AnimatedView || View : null) || BaseViewComponent
395
-
396
- elementType = Component || elementType
397
- const isStringElement = typeof elementType === 'string'
398
-
399
431
  const disabled =
400
432
  (props.accessibilityState != null && props.accessibilityState.disabled === true) ||
401
433
  props.accessibilityDisabled
@@ -404,26 +436,8 @@ export function createComponent<
404
436
  // so the type is pretty loose
405
437
  let viewProps: Record<string, any>
406
438
 
407
- const hasEnterStyle = !!props.enterStyle
408
- const shouldSetMounted = Boolean(
409
- (isWeb ? isClient : true) && (hasEnterStyle || props.animation) && !state.mounted
410
- )
411
- const setMounted = shouldSetMounted
412
- ? () => {
413
- // for some reason without some small delay it doesn't animate css
414
- setTimeout(
415
- () => {
416
- setStateShallow({
417
- mounted: true,
418
- })
419
- },
420
- isWeb ? 10 : 0
421
- )
422
- }
423
- : undefined
424
-
425
439
  // if react-native-web view just pass all props down
426
- if (process.env.TAMAGUI_TARGET === 'web' && !staticConfig.isReactNativeWeb) {
440
+ if (process.env.TAMAGUI_TARGET === 'web' && !isReactNativeWeb) {
427
441
  // otherwise replicate react-native-web functionality
428
442
  const {
429
443
  // event props
@@ -444,112 +458,14 @@ export function createComponent<
444
458
  onStartShouldSetResponder,
445
459
  onStartShouldSetResponderCapture,
446
460
 
447
- // react-native props
448
- nativeID,
449
-
450
- // react-native-web accessibility props
451
- // @ts-ignore
452
- accessibilityActiveDescendant,
453
- // @ts-ignore
454
- accessibilityAtomic,
455
- // @ts-ignore
456
- accessibilityAutoComplete,
457
- // @ts-ignore
458
- accessibilityBusy,
459
- // @ts-ignore
460
- accessibilityChecked,
461
- // @ts-ignore
462
- accessibilityColumnCount,
463
- // @ts-ignore
464
- accessibilityColumnIndex,
465
- // @ts-ignore
466
- accessibilityColumnSpan,
467
- // @ts-ignore
468
- accessibilityControls,
469
- // @ts-ignore
470
- accessibilityCurrent,
471
- // @ts-ignore
472
- accessibilityDescribedBy,
473
- // @ts-ignore
474
- accessibilityDetails,
475
- // @ts-ignore
476
- accessibilityDisabled,
477
- // @ts-ignore
478
- accessibilityErrorMessage,
479
- // @ts-ignore
480
- accessibilityExpanded,
481
- // @ts-ignore
482
- accessibilityFlowTo,
483
- // @ts-ignore
484
- accessibilityHasPopup,
485
- // @ts-ignore
486
- accessibilityHidden,
487
- // @ts-ignore
488
- accessibilityInvalid,
489
- // @ts-ignore
490
- accessibilityKeyShortcuts,
491
- // @ts-ignore
492
- accessibilityLabel,
493
- // @ts-ignore
494
- accessibilityLabelledBy,
495
- // @ts-ignore
496
- accessibilityLevel,
497
- // @ts-ignore
498
- accessibilityLiveRegion,
499
- // @ts-ignore
500
- accessibilityModal,
501
- // @ts-ignore
502
- accessibilityMultiline,
503
- // @ts-ignore
504
- accessibilityMultiSelectable,
505
- // @ts-ignore
506
- accessibilityOrientation,
507
- // @ts-ignore
508
- accessibilityOwns,
509
- // @ts-ignore
510
- accessibilityPlaceholder,
511
- // @ts-ignore
512
- accessibilityPosInSet,
513
- // @ts-ignore
514
- accessibilityPressed,
515
- // @ts-ignore
516
- accessibilityReadOnly,
517
- // @ts-ignore
518
- accessibilityRequired,
519
- // @ts-ignore
520
- accessibilityRole,
521
- // @ts-ignore
522
- accessibilityRoleDescription,
523
- // @ts-ignore
524
- accessibilityRowCount,
525
- // @ts-ignore
526
- accessibilityRowIndex,
527
- // @ts-ignore
528
- accessibilityRowSpan,
529
- // @ts-ignore
530
- accessibilitySelected,
531
- // @ts-ignore
532
- accessibilitySetSize,
533
- // @ts-ignore
534
- accessibilitySort,
535
- // @ts-ignore
536
- accessibilityValueMax,
537
- // @ts-ignore
538
- accessibilityValueMin,
539
- // @ts-ignore
540
- accessibilityValueNow,
541
- // @ts-ignore
542
- accessibilityValueText,
543
-
544
- // deprecated
545
- accessible,
546
- accessibilityState,
547
- accessibilityValue,
548
-
549
461
  // android
550
462
  collapsable,
551
463
  focusable,
552
464
 
465
+ // deprecated,
466
+ accessible,
467
+ accessibilityDisabled,
468
+
553
469
  onLayout,
554
470
 
555
471
  ...webProps
@@ -557,12 +473,11 @@ export function createComponent<
557
473
 
558
474
  viewProps = webProps
559
475
 
560
- assignNativePropsToWeb(elementType, viewProps, nonTamaguiProps)
561
-
562
476
  if (!isRSC) {
563
- useElementLayout(hostRef, onLayout)
477
+ usePlatformMethods(hostRef as RefObject<Element>)
478
+
479
+ useElementLayout(hostRef as RefObject<Element>, onLayout as any)
564
480
 
565
- // from react-native-web
566
481
  useResponderEvents(hostRef, {
567
482
  onMoveShouldSetResponder,
568
483
  onMoveShouldSetResponderCapture,
@@ -580,14 +495,7 @@ export function createComponent<
580
495
  onSelectionChangeShouldSetResponderCapture,
581
496
  onStartShouldSetResponder,
582
497
  onStartShouldSetResponderCapture,
583
- })
584
-
585
- // from react-native-web
586
- const platformMethodsRef = usePlatformMethods(viewProps)
587
-
588
- const setRef = useMergeRefs(hostRef, platformMethodsRef, forwardedRef as any, setMounted)
589
-
590
- viewProps.ref = setRef
498
+ } as any)
591
499
  }
592
500
 
593
501
  if (props.href != undefined && hrefAttrs != undefined) {
@@ -640,12 +548,10 @@ export function createComponent<
640
548
  }
641
549
  } else {
642
550
  viewProps = nonTamaguiProps
643
- if (forwardedRef) {
644
- // @ts-ignore
645
- viewProps.ref = forwardedRef
646
- }
647
551
  }
648
552
 
553
+ viewProps.ref = useComposedRefs(hostRef as any, forwardedRef, setMounted)
554
+
649
555
  if (process.env.NODE_ENV === 'development' && !isText && isWeb && !staticConfig.isHOC) {
650
556
  Children.toArray(props.children).forEach((item) => {
651
557
  if (typeof item === 'string') {
@@ -672,8 +578,6 @@ export function createComponent<
672
578
 
673
579
  let styles: any[]
674
580
 
675
- const animationStyles = state.animation ? state.animation.style : null
676
-
677
581
  if (isStringElement && shouldAvoidClasses && !shouldForcePseudo) {
678
582
  styles = {
679
583
  ...defaultNativeStyle,
@@ -705,32 +609,16 @@ export function createComponent<
705
609
  }
706
610
  }
707
611
 
708
- if (process.env.TAMAGUI_TARGET === 'web') {
709
- let fontFamily = isText
710
- ? splitStyles.fontFamily || staticConfig.defaultProps.fontFamily
711
- : null
712
- if (fontFamily && fontFamily[0] === '$') {
713
- fontFamily = fontFamily.slice(1)
714
- }
715
-
716
- if (process.env.NODE_ENV === 'development') {
717
- if (fontFamily?.startsWith(`var(`)) {
718
- // eslint-disable-next-line no-console
719
- console.warn(
720
- `Received variable instead of resolved name of font, this is a bug. Please report on Github.`,
721
- {
722
- fontFamily,
723
- props,
724
- splitStyles,
725
- staticConfig,
726
- }
727
- )
728
- }
729
- }
612
+ let fontFamily = isText ? splitStyles.fontFamily || staticConfig.defaultProps.fontFamily : null
613
+ if (fontFamily && fontFamily[0] === '$') {
614
+ fontFamily = fontFamily.slice(1)
615
+ }
616
+ const fontFamilyClassName = fontFamily ? `font_${fontFamily}` : ''
730
617
 
618
+ if (process.env.TAMAGUI_TARGET === 'web') {
731
619
  const classList = [
732
620
  componentName ? componentClassName : '',
733
- fontFamily ? `font_${fontFamily}` : '',
621
+ fontFamilyClassName,
734
622
  theme.className,
735
623
  classNames ? Object.values(classNames).join(' ') : '',
736
624
  ]
@@ -738,18 +626,9 @@ export function createComponent<
738
626
  const className = classList.join(' ')
739
627
  const style = animationStyles ?? splitStyles.style
740
628
 
741
- // TODO this is specific to reanimated rn
742
- const isAnimatedReactNativeWeb = props.animation && avoidClassesWhileAnimating
743
-
744
- // temp fix for animated react-native-web restore pre-styleq functionality
745
629
  if (isAnimatedReactNativeWeb) {
746
630
  viewProps.style = style
747
- viewProps.dataSet = {
748
- ...viewProps.dataSet,
749
- className,
750
- id: props.id,
751
- }
752
- } else if (staticConfig.isReactNativeWeb) {
631
+ } else if (isReactNativeWeb) {
753
632
  const rnwStyle = { $$css: true }
754
633
  for (const name of className.split(' ')) {
755
634
  rnwStyle[name] = name
@@ -772,13 +651,9 @@ export function createComponent<
772
651
  }
773
652
 
774
653
  if (process.env.TAMAGUI_TARGET === 'native') {
775
- // add ref
776
- const mergedRef = useMergeRefs(forwardedRef, hostRef, setMounted)
777
- viewProps.ref = mergedRef
778
-
779
654
  // swap out the right family based on weight/style
780
655
  if (splitStyles.fontFamily) {
781
- const faceInfo = config.fontsParsed[splitStyles.fontFamily]?.face
656
+ const faceInfo = tamaguiConfig.fontsParsed[splitStyles.fontFamily]?.face
782
657
  if (faceInfo) {
783
658
  const [weight, style] = (() => {
784
659
  let weight: string | undefined
@@ -820,10 +695,7 @@ export function createComponent<
820
695
  isHoverable &&
821
696
  !!((pseudos && pseudos.hoverStyle) || onHoverIn || onHoverOut || onMouseEnter || onMouseLeave)
822
697
 
823
- const handlesPressEvents = !isStringElement && !asChild
824
- const pressKey = handlesPressEvents ? 'onPress' : 'onClick'
825
- const pressInKey = handlesPressEvents ? 'onPressIn' : 'onMouseDown'
826
- const pressOutKey = handlesPressEvents ? 'onPressOut' : 'onMouseUp'
698
+ const handlesPressEvents = !isWeb && !asChild
827
699
 
828
700
  // check presence to prevent reparenting bugs, allows for onPress={x ? function : undefined} usage
829
701
  const shouldAttach =
@@ -844,7 +716,7 @@ export function createComponent<
844
716
  const events =
845
717
  shouldAttach && !isRSC
846
718
  ? {
847
- [pressOutKey]: attachPress
719
+ onPressOut: attachPress
848
720
  ? (e) => {
849
721
  unPress()
850
722
  onPressOut?.(e)
@@ -861,7 +733,7 @@ export function createComponent<
861
733
  if (state.pressIn) {
862
734
  next.press = true
863
735
  }
864
- if (Object.keys(next).length) {
736
+ if (attachHover || state.pressIn) {
865
737
  setStateShallow(next)
866
738
  }
867
739
  onHoverIn?.(e)
@@ -887,7 +759,7 @@ export function createComponent<
887
759
  }
888
760
  : undefined,
889
761
  }),
890
- [pressInKey]: attachPress
762
+ onPressIn: attachPress
891
763
  ? (e) => {
892
764
  setStateShallow({
893
765
  press: true,
@@ -900,15 +772,15 @@ export function createComponent<
900
772
  mouseUps.add(unPress)
901
773
  }
902
774
  }
903
- : null,
904
- [pressKey]: attachPress
775
+ : undefined,
776
+ onPress: attachPress
905
777
  ? (e) => {
906
778
  unPress()
907
779
  // @ts-ignore
908
780
  onClick?.(e)
909
781
  onPress?.(e)
910
782
  }
911
- : null,
783
+ : undefined,
912
784
 
913
785
  // replicating TouchableWithoutFeedback
914
786
  ...(!isWeb && {
@@ -974,33 +846,6 @@ export function createComponent<
974
846
  }
975
847
  }
976
848
 
977
- // EVENTS: web
978
- if (!isRSC && isWeb) {
979
- // eslint-disable-next-line react-hooks/rules-of-hooks
980
- const [pressableProps] = usePressable(
981
- events
982
- ? {
983
- disabled,
984
- ...(hitSlop && {
985
- hitSlop,
986
- }),
987
- onPressOut: events[pressOutKey],
988
- onPressIn: events[pressInKey],
989
- onPress: events[pressKey],
990
- }
991
- : {
992
- disabled: true,
993
- }
994
- )
995
- if (events) {
996
- if (handlesPressEvents) {
997
- Object.assign(viewProps, pressableProps)
998
- } else {
999
- Object.assign(viewProps, events)
1000
- }
1001
- }
1002
- }
1003
-
1004
849
  // EVENTS native
1005
850
  if (process.env.TAMAGUI_TARGET === 'native') {
1006
851
  // add focus events
@@ -1021,9 +866,6 @@ export function createComponent<
1021
866
  // only ever create once, use .configure() to update later
1022
867
  const pressability = usePressability(events)
1023
868
  if (attachPress && events) {
1024
- const dontComposePressabilityKeys = {
1025
- onClick: true,
1026
- }
1027
869
  if (hitSlop) {
1028
870
  viewProps.hitSlop = hitSlop
1029
871
  }
@@ -1039,33 +881,32 @@ export function createComponent<
1039
881
  content = createElement(elementType, viewProps, childEls)
1040
882
 
1041
883
  if (process.env.TAMAGUI_TARGET === 'web') {
1042
- // only necessary when animating because some AnimatedView which wraps RNW View doesn't forward dataSet className
1043
- const isAnimatedRNWView = isAnimated && typeof elementType !== 'string' // assuming for now as reanimated is only driver
1044
- const shouldWrapWithComponentTheme =
1045
- !!theme.className &&
1046
- isAnimatedRNWView &&
1047
- getReturnVariablesAs(props, splitStyleState) === 'non-color-value'
1048
- const shouldWrapWithHover = Boolean(events || isRSC) && attachHover
1049
-
1050
- if (shouldWrapWithHover || shouldWrapWithComponentTheme) {
1051
- const themeClassName = shouldWrapWithComponentTheme ? `${theme.className}` : ''
1052
- const hoverClassName = shouldWrapWithHover ? 't_Hoverable' : ''
884
+ if (events) {
1053
885
  content = (
1054
886
  <span
1055
- className={`${hoverClassName} ${themeClassName}`}
1056
- style={{
1057
- display: 'contents',
1058
- }}
1059
- {...(events &&
1060
- shouldWrapWithHover && {
1061
- onMouseEnter: events.onMouseEnter,
1062
- onMouseLeave: events.onMouseLeave,
1063
- })}
887
+ style={styleDisplayContents}
888
+ onMouseEnter={events.onMouseEnter}
889
+ onMouseLeave={events.onMouseLeave}
890
+ onClick={events.onPress}
891
+ onMouseDown={events.onPressIn}
892
+ onMouseUp={events.onPressOut}
893
+ onTouchStart={events.onPressIn}
894
+ onTouchEnd={events.onPressOut}
1064
895
  >
1065
896
  {content}
1066
897
  </span>
1067
898
  )
1068
899
  }
900
+
901
+ // special weird case since there's a bug in RNW where we can't animate + pass style { $$css }
902
+ // but we need is_font classnames... need to see about RNW bug and then can remove this
903
+ if (isText && isAnimatedReactNativeWeb) {
904
+ content = (
905
+ <span className={fontFamilyClassName} style={styleDisplayContents}>
906
+ {content}
907
+ </span>
908
+ )
909
+ }
1069
910
  }
1070
911
 
1071
912
  if (process.env.NODE_ENV === 'development') {
@@ -1098,48 +939,44 @@ export function createComponent<
1098
939
  component.displayName = staticConfig.componentName
1099
940
  }
1100
941
 
1101
- // Once configuration is run and all components are registered
1102
- // get default props + className and analyze styles
1103
942
  onConfiguredOnce((conf) => {
1104
- if (!defaultComponentState) {
1105
- defaultComponentState = Object.freeze({
1106
- hover: false,
1107
- press: false,
1108
- pressIn: false,
1109
- focus: false,
1110
- // only used by enterStyle
1111
- mounted: false,
1112
- animation: null,
1113
- mediaState: getInitialMediaState(),
1114
- })
1115
- }
1116
-
1117
- // in static mode we just use these to lookup configuration
1118
- // ... we likely want this? need to test
1119
- if (process.env.IS_STATIC === 'is_static') return
1120
-
1121
- tamaguiConfig = conf
1122
-
1123
- // do this to make sure shorthands don't duplicate with.. longhands
1124
- mergeShorthands(staticConfig, tamaguiConfig)
943
+ // one time only setup
944
+ if (!tamaguiConfig) {
945
+ tamaguiConfig = conf
946
+
947
+ if (!defaultComponentState) {
948
+ defaultComponentState = {
949
+ hover: false,
950
+ press: false,
951
+ pressIn: false,
952
+ focus: false,
953
+ mounted: false,
954
+ mediaState: getInitialMediaState(),
955
+ }
956
+ defaultComponentStateMounted = {
957
+ ...defaultComponentState,
958
+ mounted: true,
959
+ }
960
+ }
1125
961
 
1126
- if (tamaguiConfig.animations) {
1127
- avoidClassesWhileAnimating = !!tamaguiConfig.animations.avoidClasses
1128
- AnimatedText = tamaguiConfig.animations.Text
1129
- AnimatedView = tamaguiConfig.animations.View
1130
- }
962
+ if (tamaguiConfig.animations) {
963
+ AnimatedText = tamaguiConfig.animations.Text
964
+ AnimatedView = tamaguiConfig.animations.View
965
+ }
1131
966
 
1132
- if (!initialTheme) {
1133
- const next = conf.themes[conf.defaultTheme || Object.keys(conf.themes)[0]]
1134
- initialTheme = proxyThemeVariables(next)
1135
- if (!initialTheme && process.env.NODE_ENV === 'development') {
1136
- // eslint-disable-next-line no-console
1137
- console.log(`Warning: Missing theme`)
967
+ if (!initialTheme) {
968
+ const next = conf.themes[conf.defaultTheme || Object.keys(conf.themes)[0]]
969
+ initialTheme = proxyThemeVariables(next)
970
+ if (!initialTheme && process.env.NODE_ENV === 'development') {
971
+ // eslint-disable-next-line no-console
972
+ console.log(`Warning: Missing theme`)
973
+ }
1138
974
  }
1139
975
  }
1140
976
 
1141
- // adds in user defined default props
1142
- config = getConfig()
977
+ // per-component setup
978
+ // do this to make sure shorthands don't duplicate with.. longhands
979
+ mergeShorthands(staticConfig, tamaguiConfig)
1143
980
 
1144
981
  let defaultPropsIn = staticConfig.defaultProps || {}
1145
982
 
@@ -1148,23 +985,18 @@ export function createComponent<
1148
985
  // find last unprocessed and process
1149
986
  const parentNames = [...(staticConfig.parentNames || []), staticConfig.componentName]
1150
987
 
1151
- if (config.defaultProps && parentNames && staticConfig.componentName) {
988
+ if (tamaguiConfig.defaultProps && parentNames && staticConfig.componentName) {
1152
989
  defaultPropsIn = mergeConfigDefaultProps(
1153
990
  staticConfig.componentName,
1154
991
  defaultPropsIn,
1155
- config.defaultProps,
992
+ tamaguiConfig.defaultProps,
1156
993
  parentNames,
1157
- conf
994
+ tamaguiConfig
1158
995
  )
1159
996
  }
1160
997
 
1161
998
  const debug = defaultPropsIn['debug']
1162
999
 
1163
- if (process.env.NODE_ENV === 'development' && debug === 'break') {
1164
- // eslint-disable-next-line no-debugger
1165
- debugger
1166
- }
1167
-
1168
1000
  // remove all classNames
1169
1001
  const [parentProps, parentClassNames] = mergeProps(defaultPropsIn, {}, true)
1170
1002
 
@@ -1286,12 +1118,14 @@ export const Spacer = createComponent<SpacerProps>({
1286
1118
  memo: true,
1287
1119
  componentName: 'Spacer',
1288
1120
  validStyles,
1121
+
1289
1122
  defaultProps: {
1290
1123
  ...stackDefaultStyles,
1291
1124
  // avoid nesting issues
1292
1125
  tag: 'span',
1293
1126
  size: true,
1294
1127
  },
1128
+
1295
1129
  variants: {
1296
1130
  size: {
1297
1131
  '...size': (size, { tokens }) => {
@@ -1324,10 +1158,6 @@ export const Spacer = createComponent<SpacerProps>({
1324
1158
  both: {},
1325
1159
  },
1326
1160
  } as const,
1327
-
1328
- defaultVariants: {
1329
- direction: 'both',
1330
- },
1331
1161
  })
1332
1162
 
1333
1163
  export type SpacedChildrenProps = {
@@ -1387,7 +1217,7 @@ export function spacedChildren({
1387
1217
  if (hasSpace) {
1388
1218
  final.push(
1389
1219
  createSpacer({
1390
- key: `_${index}_before_sep_spacer`,
1220
+ key: `_${index}_00tmgui`,
1391
1221
  direction,
1392
1222
  space,
1393
1223
  spaceFlex,
@@ -1402,7 +1232,7 @@ export function spacedChildren({
1402
1232
  if (hasSpace) {
1403
1233
  final.push(
1404
1234
  createSpacer({
1405
- key: `_${index}_after_sep_spacer`,
1235
+ key: `_${index}01tmgui`,
1406
1236
  direction,
1407
1237
  space,
1408
1238
  spaceFlex,
@@ -1412,7 +1242,7 @@ export function spacedChildren({
1412
1242
  } else {
1413
1243
  final.push(
1414
1244
  createSpacer({
1415
- key: `_${index}_spacer`,
1245
+ key: `_${index}02tmgui`,
1416
1246
  direction,
1417
1247
  space,
1418
1248
  spaceFlex,
@@ -1446,48 +1276,6 @@ function isUnspaced(child: React.ReactNode) {
1446
1276
  return child?.['type']?.['isVisuallyHidden'] || child?.['type']?.['isUnspaced']
1447
1277
  }
1448
1278
 
1449
- function AbsoluteFill(props: { children?: any }) {
1450
- return (
1451
- <View pointerEvents="box-none" style={absoluteFill}>
1452
- {props.children}
1453
- </View>
1454
- )
1455
- }
1456
-
1457
- const absoluteFill = {
1458
- position: 'absolute',
1459
- top: 0,
1460
- left: 0,
1461
- right: 0,
1462
- bottom: 0,
1463
- } as const
1464
-
1465
- // this can be done with CSS entirely right?
1466
- // const shouldWrapTextAncestor = isWeb && isText && !hasTextAncestor
1467
- // if (shouldWrapTextAncestor) {
1468
- // // from react-native-web
1469
- // content = createElement(TextAncestorContext.Provider, { value: true }, content)
1470
- // }
1471
-
1472
- export function processIDRefList(idRefList: string | Array<string>): string {
1473
- return Array.isArray(idRefList) ? idRefList.join(' ') : idRefList
1474
- }
1475
-
1476
- export const accessibilityRoleToWebRole = {
1477
- adjustable: 'slider',
1478
- button: 'button',
1479
- header: 'heading',
1480
- image: 'img',
1481
- imagebutton: null,
1482
- keyboardkey: null,
1483
- label: null,
1484
- link: 'link',
1485
- none: 'presentation',
1486
- search: 'search',
1487
- summary: 'region',
1488
- text: null,
1489
- }
1490
-
1491
1279
  function addPseudoToStyles(
1492
1280
  styles: any[],
1493
1281
  initialPseudos: SplitStyleResult['pseudos'],
@@ -1608,3 +1396,45 @@ function merge(base: ViewStyle, next: ViewStyle) {
1608
1396
  }
1609
1397
  }
1610
1398
  }
1399
+
1400
+ // react native compat (web only)
1401
+ function usePlatformMethods(hostRef: RefObject<Element>) {
1402
+ useIsomorphicLayoutEffect(() => {
1403
+ const node = hostRef.current
1404
+ if (!node) return
1405
+ // @ts-ignore
1406
+ node.measure = (callback) => measureLayout(node, null, callback)
1407
+ // @ts-ignore
1408
+ node.measureLayout = (relativeToNode, success) => measureLayout(node, relativeToNode, success)
1409
+ // @ts-ignore
1410
+ node.measureInWindow = (callback) => {
1411
+ if (!node) return
1412
+ setTimeout(() => {
1413
+ const { height, left, top, width } = getRect(node as HTMLElement)!
1414
+ callback(left, top, width, height)
1415
+ }, 0)
1416
+ }
1417
+ }, [hostRef])
1418
+ }
1419
+
1420
+ const AbsoluteFill: any = createComponent({
1421
+ componentName: 'AbsoluteFill',
1422
+ defaultProps: {
1423
+ ...stackDefaultStyles,
1424
+ flexDirection: 'column',
1425
+ position: 'absolute',
1426
+ top: 0,
1427
+ right: 0,
1428
+ bottom: 0,
1429
+ left: 0,
1430
+ pointerEvents: 'box-none',
1431
+ },
1432
+ })
1433
+
1434
+ const styleDisplayContents = {
1435
+ display: 'contents',
1436
+ }
1437
+
1438
+ const dontComposePressabilityKeys = {
1439
+ onClick: true,
1440
+ }