@mpxjs/webpack-plugin 2.9.62 → 2.9.64

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 (86) hide show
  1. package/lib/index.js +1 -3
  2. package/lib/platform/style/wx/index.js +67 -53
  3. package/lib/react/processStyles.js +1 -0
  4. package/lib/react/processTemplate.js +2 -3
  5. package/lib/react/style-helper.js +12 -7
  6. package/lib/runtime/components/react/context.ts +9 -7
  7. package/lib/runtime/components/react/dist/context.js +1 -0
  8. package/lib/runtime/components/react/dist/getInnerListeners.js +12 -1
  9. package/lib/runtime/components/react/dist/mpx-button.jsx +52 -74
  10. package/lib/runtime/components/react/dist/mpx-checkbox-group.jsx +19 -18
  11. package/lib/runtime/components/react/dist/mpx-checkbox.jsx +28 -41
  12. package/lib/runtime/components/react/dist/mpx-form.jsx +16 -14
  13. package/lib/runtime/components/react/dist/mpx-icon.jsx +14 -17
  14. package/lib/runtime/components/react/dist/mpx-image/index.jsx +34 -33
  15. package/lib/runtime/components/react/dist/mpx-image/svg.jsx +3 -1
  16. package/lib/runtime/components/react/dist/mpx-input.jsx +35 -31
  17. package/lib/runtime/components/react/dist/mpx-label.jsx +29 -37
  18. package/lib/runtime/components/react/dist/mpx-movable-area.jsx +13 -18
  19. package/lib/runtime/components/react/dist/mpx-movable-view.jsx +8 -8
  20. package/lib/runtime/components/react/dist/mpx-picker/index.jsx +9 -9
  21. package/lib/runtime/components/react/dist/mpx-picker/multiSelector.jsx +7 -4
  22. package/lib/runtime/components/react/dist/mpx-picker/region.jsx +11 -7
  23. package/lib/runtime/components/react/dist/mpx-picker/selector.jsx +1 -1
  24. package/lib/runtime/components/react/dist/mpx-picker/time.jsx +18 -18
  25. package/lib/runtime/components/react/dist/mpx-picker-view-column.jsx +102 -10
  26. package/lib/runtime/components/react/dist/mpx-picker-view.jsx +147 -53
  27. package/lib/runtime/components/react/dist/mpx-radio-group.jsx +19 -18
  28. package/lib/runtime/components/react/dist/mpx-radio.jsx +28 -43
  29. package/lib/runtime/components/react/dist/mpx-root-portal.jsx +8 -4
  30. package/lib/runtime/components/react/dist/mpx-scroll-view.jsx +33 -26
  31. package/lib/runtime/components/react/dist/mpx-swiper/carouse.jsx +139 -74
  32. package/lib/runtime/components/react/dist/mpx-swiper/index.jsx +14 -6
  33. package/lib/runtime/components/react/dist/mpx-swiper-item.jsx +19 -11
  34. package/lib/runtime/components/react/dist/mpx-switch.jsx +17 -14
  35. package/lib/runtime/components/react/dist/mpx-text.jsx +19 -35
  36. package/lib/runtime/components/react/dist/mpx-textarea.jsx +1 -1
  37. package/lib/runtime/components/react/dist/mpx-view.jsx +284 -209
  38. package/lib/runtime/components/react/dist/mpx-web-view.jsx +8 -5
  39. package/lib/runtime/components/react/dist/parser.js +218 -0
  40. package/lib/runtime/components/react/dist/utils.jsx +433 -0
  41. package/lib/runtime/components/react/getInnerListeners.ts +18 -8
  42. package/lib/runtime/components/react/mpx-button.tsx +81 -91
  43. package/lib/runtime/components/react/mpx-checkbox-group.tsx +48 -43
  44. package/lib/runtime/components/react/mpx-checkbox.tsx +52 -63
  45. package/lib/runtime/components/react/mpx-form.tsx +49 -21
  46. package/lib/runtime/components/react/mpx-icon.tsx +30 -27
  47. package/lib/runtime/components/react/mpx-image/index.tsx +52 -46
  48. package/lib/runtime/components/react/mpx-image/svg.tsx +5 -3
  49. package/lib/runtime/components/react/mpx-input.tsx +58 -38
  50. package/lib/runtime/components/react/mpx-label.tsx +54 -59
  51. package/lib/runtime/components/react/mpx-movable-area.tsx +38 -24
  52. package/lib/runtime/components/react/mpx-movable-view.tsx +27 -28
  53. package/lib/runtime/components/react/mpx-navigator.tsx +2 -2
  54. package/lib/runtime/components/react/mpx-picker/date.tsx +2 -3
  55. package/lib/runtime/components/react/mpx-picker/index.tsx +10 -10
  56. package/lib/runtime/components/react/mpx-picker/multiSelector.tsx +15 -12
  57. package/lib/runtime/components/react/mpx-picker/region.tsx +21 -18
  58. package/lib/runtime/components/react/mpx-picker/selector.tsx +5 -6
  59. package/lib/runtime/components/react/mpx-picker/time.tsx +25 -29
  60. package/lib/runtime/components/react/mpx-picker/type.ts +1 -1
  61. package/lib/runtime/components/react/mpx-picker-view-column.tsx +148 -20
  62. package/lib/runtime/components/react/mpx-picker-view.tsx +179 -63
  63. package/lib/runtime/components/react/mpx-radio-group.tsx +50 -47
  64. package/lib/runtime/components/react/mpx-radio.tsx +56 -72
  65. package/lib/runtime/components/react/mpx-root-portal.tsx +10 -8
  66. package/lib/runtime/components/react/mpx-scroll-view.tsx +133 -103
  67. package/lib/runtime/components/react/mpx-swiper/carouse.tsx +174 -96
  68. package/lib/runtime/components/react/mpx-swiper/index.tsx +18 -9
  69. package/lib/runtime/components/react/mpx-swiper/type.ts +16 -5
  70. package/lib/runtime/components/react/mpx-swiper-item.tsx +46 -13
  71. package/lib/runtime/components/react/mpx-switch.tsx +44 -23
  72. package/lib/runtime/components/react/mpx-text.tsx +37 -45
  73. package/lib/runtime/components/react/mpx-textarea.tsx +1 -1
  74. package/lib/runtime/components/react/mpx-view.tsx +388 -240
  75. package/lib/runtime/components/react/mpx-web-view.tsx +19 -20
  76. package/lib/runtime/components/react/parser.ts +245 -0
  77. package/lib/runtime/components/react/types/common.ts +4 -4
  78. package/lib/runtime/components/react/types/global.d.ts +14 -2
  79. package/lib/runtime/components/react/useNodesRef.ts +1 -2
  80. package/lib/runtime/components/react/utils.tsx +505 -0
  81. package/lib/template-compiler/compiler.js +28 -20
  82. package/lib/template-compiler/gen-node-react.js +1 -3
  83. package/lib/web/processStyles.js +2 -5
  84. package/package.json +6 -4
  85. package/lib/runtime/components/react/dist/utils.js +0 -148
  86. package/lib/runtime/components/react/utils.ts +0 -170
@@ -1,16 +1,16 @@
1
1
  import { View } from 'react-native'
2
- import React, { forwardRef, useState, useRef, useEffect } from 'react'
3
- import { PickerView } from '@ant-design/react-native'
4
- import useInnerProps from './getInnerListeners'
5
- import { getCustomEvent } from './getInnerListeners'
2
+ import { LinearGradient, LinearGradientProps } from 'react-native-linear-gradient'
3
+ import React, { forwardRef, useState, useRef, ReactElement, JSX } from 'react'
4
+ import useInnerProps, { getCustomEvent } from './getInnerListeners'
6
5
  import useNodesRef, { HandlerRef } from './useNodesRef' // 引入辅助函数
6
+ import { parseInlineStyle, useTransformStyle, splitStyle, splitProps, useLayout, wrapChildren } from './utils'
7
7
  /**
8
8
  * ✔ value
9
9
  * ✔ bindchange
10
10
  * ✘ bindpickstart
11
11
  * ✘ bindpickend
12
12
  * ✘ mask-class
13
- * indicator-style
13
+ * indicator-style: 优先级indicator-style.height > pick-view-column中的子元素设置的height
14
14
  * ✘ indicator-class
15
15
  * ✘ mask-style
16
16
  * ✘ immediate-change
@@ -21,84 +21,200 @@ interface PickerViewProps {
21
21
  // 初始的defaultValue数组中的数字依次表示 picker-view 内的 picker-view-column 选择的第几项(下标从 0 开始),数字大于 picker-view-column 可选项长度时,选择最后一项。
22
22
  value?: Array<number>
23
23
  bindchange?: Function
24
+ style: {
25
+ [key: string]: any
26
+ }
27
+ 'indicator-style'?: string
28
+ 'enable-var': boolean
29
+ 'external-var-context'?: Record<string, any>,
30
+ 'enable-offset': boolean
31
+ }
32
+
33
+ interface PickerLayout {
34
+ height: number,
35
+ itemHeight: number
36
+ }
37
+
38
+ interface PosType {
39
+ height?: number,
40
+ top?: number
24
41
  }
25
42
 
43
+ const styles: { [key: string]: Object } = {
44
+ wrapper: {
45
+ display: 'flex',
46
+ flex: 1,
47
+ flexDirection: 'row',
48
+ justifyContent: 'space-around',
49
+ overflow: 'hidden',
50
+ alignItems: 'center'
51
+ },
52
+ maskTop: {
53
+ position: 'absolute',
54
+ width: 1000,
55
+ zIndex: 100
56
+ },
57
+ maskBottom: {
58
+ position: 'absolute',
59
+ width: 1000,
60
+ zIndex: 100
61
+ }
62
+ }
26
63
  const _PickerView = forwardRef<HandlerRef<View, PickerViewProps>, PickerViewProps>((props: PickerViewProps, ref) => {
27
- const { children, ...restProps } = props
28
- const layoutRef = useRef({})
29
- const { nodeRef } = useNodesRef(props, ref, {})
30
- const [value, setValue] = useState(props.value)
31
- useEffect(() => {
32
- // 确认这个是变化的props变化的时候才执行,还是初始化的时候就执行
33
- setValue(props.value)
34
- }, [props.value]);
64
+ const { children, value = [], bindchange, style, 'enable-var': enableVar, 'external-var-context': externalVarContext } = props
65
+ // indicatorStyle 需要转换为rn的style
66
+ // 微信设置到pick-view上上设置的normalStyle如border等需要转换成RN的style然后进行透传
67
+ const indicatorStyle = parseInlineStyle(props['indicator-style'])
68
+ const { height: indicatorH, width: indicatorW } = indicatorStyle
69
+ const { nodeRef } = useNodesRef<View, PickerViewProps>(props, ref, {})
70
+ // picker-view 设置的color等textStyle,在小程序上的表现是可以继承到最内层的text样式, 但是RN内部column是slot无法设置, 需要业务自己在column内的元素上设置
71
+ const {
72
+ normalStyle,
73
+ hasVarDec,
74
+ varContextRef,
75
+ hasSelfPercent,
76
+ setWidth,
77
+ setHeight
78
+ } = useTransformStyle(style, { enableVar, externalVarContext })
79
+ const { textStyle } = splitStyle(normalStyle)
80
+ const { textProps } = splitProps(props)
81
+ const {
82
+ // 存储layout布局信息
83
+ layoutRef,
84
+ layoutProps,
85
+ layoutStyle
86
+ } = useLayout({ props, hasSelfPercent, setWidth, setHeight, nodeRef: nodeRef })
35
87
 
36
- const onLayout = () => {
37
- nodeRef.current?.measure((x: number, y: number, width: number, height: number, offsetLeft: number, offsetTop: number) => {
38
- layoutRef.current = { x, y, width, height, offsetLeft, offsetTop }
39
- })
88
+ const isSetW = indicatorW !== undefined ? 1 : 0
89
+ const cloneRef = useRef(null)
90
+ const maskPos: PosType = {}
91
+ let [pickH, setPickH] = useState(0)
92
+ const itemH = pickH / 5
93
+ if (normalStyle?.height && pickH && pickH !== normalStyle?.height) {
94
+ maskPos.height = itemH * 2 + Math.ceil((normalStyle.height - pickH) / 2)
95
+ } else {
96
+ maskPos.height = itemH * 2
40
97
  }
41
- const innerProps = useInnerProps(props, {}, [], { layoutRef })
42
98
 
99
+ const onColumnLayoutChange = (layoutConfig: PickerLayout) => {
100
+ pickH = layoutConfig.height
101
+ setPickH(layoutConfig.height)
102
+ }
43
103
 
44
- const onChange = (val: Array<number>): void => {
45
- const eventData = getCustomEvent('change', {}, { detail: {value: val, source: 'touch' }, layoutRef: layoutRef })
46
- setValue(val)
47
- props.bindchange && props.bindchange(eventData)
104
+ const onSelectChange = (columnIndex: number, selIndex: number) => {
105
+ const changeValue = value.slice()
106
+ changeValue[columnIndex] = selIndex
107
+ const eventData = getCustomEvent('change', {}, { detail: { value: changeValue, source: 'change' }, layoutRef })
108
+ bindchange && bindchange(eventData)
48
109
  }
49
110
 
50
- const joinString = (data: string | any[] | React.ReactElement): string => {
51
- return (Array.isArray(data) ? data : [data]).join('')
111
+ const innerProps = useInnerProps(props, {
112
+ ref: nodeRef,
113
+ style: {
114
+ ...normalStyle,
115
+ ...layoutStyle,
116
+ position: 'relative',
117
+ overflow: 'hidden'
118
+ },
119
+ ...layoutProps
120
+ }, [
121
+ 'enable-offset'
122
+ ], { layoutRef })
123
+
124
+ const cloneChild = (child: React.ReactNode, index: number) => {
125
+ // const extraProps = index === 0 ? { getInnerLayout: getInnerLayout, innerProps } : {}
126
+ const extraProps = {}
127
+ const childProps = {
128
+ ...(child as ReactElement)?.props,
129
+ ref: cloneRef,
130
+ prefix: index,
131
+ key: 'pick-view' + index,
132
+ wrapperStyle: {
133
+ height: normalStyle?.height || 0,
134
+ itemHeight: indicatorH || 0
135
+ },
136
+ onColumnLayoutChange,
137
+ onSelectChange: onSelectChange.bind(null, index),
138
+ selectedIndex: value?.[index] || 0,
139
+ ...extraProps
140
+ }
141
+ const realElement = React.cloneElement(child as ReactElement, childProps)
142
+ return wrapChildren(
143
+ {
144
+ children: realElement
145
+ },
146
+ {
147
+ hasVarDec,
148
+ varContext: varContextRef.current,
149
+ textStyle,
150
+ textProps
151
+ }
152
+ )
52
153
  }
53
154
 
54
- const getLabelFromChildren = (child: React.ReactElement): string => {
55
- return child.props && child.props.children ? getLabelFromChildren(child.props.children) : joinString(child)
155
+ const renderTopMask = () => {
156
+ const linearProps: LinearGradientProps = {
157
+ colors: ['rgba(255,255,255,0.8)', 'rgba(255,255,255,0.2)'],
158
+ style: [
159
+ styles.maskTop,
160
+ {
161
+ height: maskPos.height,
162
+ top: 0,
163
+ pointerEvents: 'none'
164
+ }
165
+ ]
166
+ }
167
+ return (<LinearGradient {...linearProps}/>)
56
168
  }
57
169
 
58
- const handleChildren = (children: React.ReactNode[]): any[] => {
59
- return children.map((child: any, index: number) => {
60
- return {
61
- label: getLabelFromChildren(child),
62
- value: index
63
- }
64
- })
170
+ const renderBottomMask = () => {
171
+ const linearProps: LinearGradientProps = {
172
+ colors: ['rgba(255,255,255,0.2)', 'rgba(255,255,255,0.8)'],
173
+ style: [
174
+ styles.maskBottom,
175
+ {
176
+ height: maskPos.height,
177
+ bottom: 0,
178
+ pointerEvents: 'none'
179
+ }
180
+ ]
181
+ }
182
+ return <LinearGradient {...linearProps}></LinearGradient>
65
183
  }
66
184
 
67
- const getDataFromChildren = (children: React.ReactNode): any[] => {
68
- return (Array.isArray(children) ? children : [children]).map((child: any) => {
69
- return handleChildren(child.props && child.props.children ? child.props.children : [child])
70
- })
185
+ const renderLine = () => {
186
+ return <View style={[{
187
+ position: 'absolute',
188
+ top: '50%',
189
+ transform: [{ translateY: -(itemH / 2) }],
190
+ height: itemH,
191
+ borderTopWidth: 1,
192
+ borderBottomWidth: 1,
193
+ borderColor: '#f0f0f0',
194
+ width: '100%',
195
+ zIndex: 101
196
+ }]}></View>
71
197
  }
72
198
 
73
- const columns = Array.isArray(children) ? children.length : 1
74
- const originData = getDataFromChildren(children)
75
- // 子节点默认的序号,这里是更新默认值的
76
- const subChildLength = originData.map((item) => {
77
- return item.length
78
- })
79
- const defaultValue = (props.value || []).map((item, index) => {
80
- if (item > subChildLength[index]) {
81
- return subChildLength[index] - 1
199
+ const renderSubChild = () => {
200
+ if (Array.isArray(children)) {
201
+ return children.map((item, index) => {
202
+ return cloneChild(item, index)
203
+ })
82
204
  } else {
83
- return item
205
+ return cloneChild(children, 0)
84
206
  }
85
- })
86
-
87
- return (
88
- <PickerView
89
- {...restProps}
90
- cols={columns}
91
- // 默认选中项
92
- defaultValue={defaultValue}
93
- // 内部维护选中项
94
- value={value}
95
- // data数据源column
96
- data={originData}
97
- onChange={onChange}
98
- cascade={false}/>
99
- )
207
+ }
208
+ return (<View {...innerProps}>
209
+ {renderTopMask()}
210
+ <View style={[styles.wrapper]}>
211
+ {renderSubChild()}
212
+ </View>
213
+ {renderBottomMask()}
214
+ {!isSetW && renderLine()}
215
+ </View>)
100
216
  })
101
217
 
102
- _PickerView.displayName = 'mpx-picker-view';
218
+ _PickerView.displayName = 'mpx-picker-view'
103
219
 
104
220
  export default _PickerView
@@ -1,47 +1,44 @@
1
1
  /**
2
2
  * ✔ bindchange
3
3
  */
4
- import {
5
- JSX,
6
- useRef,
7
- forwardRef,
8
- ReactNode,
9
- useContext
10
- } from 'react'
11
- import {
12
- View,
13
- NativeSyntheticEvent,
14
- ViewStyle
15
- } from 'react-native'
4
+ import { JSX, useRef, forwardRef, ReactNode, useContext } from 'react'
5
+ import { View, NativeSyntheticEvent, ViewStyle } from 'react-native'
6
+ import { warn } from '@mpxjs/utils'
16
7
  import { FormContext, FormFieldValue, RadioGroupContext, GroupValue } from './context'
17
8
  import useInnerProps, { getCustomEvent } from './getInnerListeners'
18
9
  import useNodesRef, { HandlerRef } from './useNodesRef'
19
- import { throwReactWarning } from './utils'
10
+ import { useLayout, useTransformStyle, wrapChildren } from './utils'
20
11
 
21
- export interface radioGroupProps {
12
+ export interface RadioGroupProps {
22
13
  name: string
23
14
  style?: ViewStyle & Record<string, any>
24
15
  'enable-offset'?: boolean
16
+ 'enable-var'?: boolean
17
+ 'external-var-context'?: Record<string, any>
18
+ 'parent-font-size'?: number
19
+ 'parent-width'?: number
20
+ 'parent-height'?: number
25
21
  children: ReactNode
26
22
  bindchange?: (evt: NativeSyntheticEvent<TouchEvent> | unknown) => void
27
23
  }
28
24
 
29
25
  const radioGroup = forwardRef<
30
- HandlerRef<View, radioGroupProps>,
31
- radioGroupProps
26
+ HandlerRef<View, RadioGroupProps>,
27
+ RadioGroupProps
32
28
  >((props, ref): JSX.Element => {
33
29
  const {
34
30
  style = {},
35
- 'enable-offset': enableOffset,
36
- children,
37
- bindchange,
31
+ 'enable-var': enableVar,
32
+ 'external-var-context': externalVarContext,
33
+ 'parent-font-size': parentFontSize,
34
+ 'parent-width': parentWidth,
35
+ 'parent-height': parentHeight,
36
+ bindchange
38
37
  } = props
39
38
 
40
- const layoutRef = useRef({})
41
-
42
39
  const formContext = useContext(FormContext)
43
40
 
44
- let formValuesMap: Map<string, FormFieldValue> | undefined;
41
+ let formValuesMap: Map<string, FormFieldValue> | undefined
45
42
 
46
43
  if (formContext) {
47
44
  formValuesMap = formContext.formValuesMap
@@ -51,31 +48,29 @@ const radioGroup = forwardRef<
51
48
 
52
49
  const defaultStyle = {
53
50
  flexDirection: 'row',
54
- flexWrap: 'wrap',
55
- ...style
51
+ flexWrap: 'wrap'
56
52
  }
57
53
 
58
- const { nodeRef } = useNodesRef(props, ref, {
59
- defaultStyle
60
- })
61
-
62
- const onLayout = () => {
63
- nodeRef.current?.measure(
64
- (
65
- x: number,
66
- y: number,
67
- width: number,
68
- height: number,
69
- offsetLeft: number,
70
- offsetTop: number
71
- ) => {
72
- layoutRef.current = { x, y, width, height, offsetLeft, offsetTop }
73
- }
74
- )
54
+ const styleObj = {
55
+ ...defaultStyle,
56
+ ...style
75
57
  }
76
58
 
59
+ const {
60
+ hasSelfPercent,
61
+ normalStyle,
62
+ hasVarDec,
63
+ varContextRef,
64
+ setWidth,
65
+ setHeight
66
+ } = useTransformStyle(styleObj, { enableVar, externalVarContext, parentFontSize, parentWidth, parentHeight })
67
+
68
+ const { nodeRef } = useNodesRef(props, ref, { defaultStyle })
69
+
70
+ const { layoutRef, layoutStyle, layoutProps } = useLayout({ props, hasSelfPercent, setWidth, setHeight, nodeRef })
71
+
77
72
  const getSelectionValue = (): string | undefined => {
78
- for (let key in groupValue) {
73
+ for (const key in groupValue) {
79
74
  if (groupValue[key].checked) {
80
75
  return key
81
76
  }
@@ -95,7 +90,7 @@ const radioGroup = forwardRef<
95
90
 
96
91
  if (formValuesMap) {
97
92
  if (!props.name) {
98
- throwReactWarning('[Mpx runtime warn]: If a form component is used, the name attribute is required.')
93
+ warn('If a form component is used, the name attribute is required.')
99
94
  } else {
100
95
  formValuesMap.set(props.name, { getValue, resetValue })
101
96
  }
@@ -124,10 +119,10 @@ const radioGroup = forwardRef<
124
119
  props,
125
120
  {
126
121
  ref: nodeRef,
127
- style: defaultStyle,
128
- ...(enableOffset ? { onLayout } : {})
122
+ style: { ...normalStyle, ...layoutStyle },
123
+ ...layoutProps
129
124
  },
130
- ['enable-offset'],
125
+ [],
131
126
  {
132
127
  layoutRef
133
128
  }
@@ -136,7 +131,15 @@ const radioGroup = forwardRef<
136
131
  return (
137
132
  <View {...innerProps}>
138
133
  <RadioGroupContext.Provider value={{ groupValue, notifyChange }}>
139
- {children}
134
+ {
135
+ wrapChildren(
136
+ props,
137
+ {
138
+ hasVarDec,
139
+ varContext: varContextRef.current
140
+ }
141
+ )
142
+ }
140
143
  </RadioGroupContext.Provider>
141
144
  </View>
142
145
  )
@@ -4,19 +4,13 @@
4
4
  * ✔ checked
5
5
  * ✔ color
6
6
  */
7
- import { JSX, useRef, useState, forwardRef, useEffect, ReactNode, useContext, Dispatch, SetStateAction } from 'react'
8
- import {
9
- View,
10
- Text,
11
- StyleSheet,
12
- ViewStyle,
13
- NativeSyntheticEvent,
14
- TextStyle
15
- } from 'react-native'
7
+ import { JSX, useState, forwardRef, useEffect, ReactNode, useContext, Dispatch, SetStateAction } from 'react'
8
+ import { View, StyleSheet, ViewStyle, NativeSyntheticEvent } from 'react-native'
9
+ import { warn } from '@mpxjs/utils'
16
10
  import { LabelContext, RadioGroupContext } from './context'
17
11
  import useInnerProps, { getCustomEvent } from './getInnerListeners'
18
12
  import useNodesRef, { HandlerRef } from './useNodesRef'
19
- import { every, splitStyle, splitProps, isText, throwReactWarning } from './utils'
13
+ import { splitProps, splitStyle, useLayout, useTransformStyle, wrapChildren } from './utils'
20
14
  import Icon from './mpx-icon'
21
15
 
22
16
  export interface RadioProps {
@@ -26,6 +20,11 @@ export interface RadioProps {
26
20
  color?: string
27
21
  style?: ViewStyle & Record<string, any>
28
22
  'enable-offset'?: boolean
23
+ 'enable-var'?: boolean
24
+ 'external-var-context'?: Record<string, any>
25
+ 'parent-font-size'?: number;
26
+ 'parent-width'?: number;
27
+ 'parent-height'?: number;
29
28
  children: ReactNode
30
29
  bindtap?: (evt: NativeSyntheticEvent<TouchEvent> | unknown) => void
31
30
  catchtap?: (evt: NativeSyntheticEvent<TouchEvent> | unknown) => void
@@ -66,44 +65,41 @@ const styles = StyleSheet.create({
66
65
  })
67
66
 
68
67
  const Radio = forwardRef<HandlerRef<View, RadioProps>, RadioProps>(
69
- (props, ref): JSX.Element => {
68
+ (radioProps, ref): JSX.Element => {
69
+ const { textProps, innerProps: props = {} } = splitProps(radioProps)
70
+
70
71
  const {
71
72
  value = '',
72
73
  disabled = false,
73
74
  checked = false,
74
75
  color = '#09BB07',
75
76
  style = [],
76
- 'enable-offset': enableOffset,
77
- children,
77
+ 'enable-var': enableVar,
78
+ 'external-var-context': externalVarContext,
79
+ 'parent-font-size': parentFontSize,
80
+ 'parent-width': parentWidth,
81
+ 'parent-height': parentHeight,
78
82
  bindtap,
79
- catchtap,
83
+ catchtap
80
84
  } = props
81
85
 
82
- const layoutRef = useRef({})
83
-
84
86
  const [isChecked, setIsChecked] = useState<boolean>(!!checked)
85
87
 
86
88
  const groupContext = useContext(RadioGroupContext)
87
- let groupValue: { [key: string]: { checked: boolean; setValue: Dispatch<SetStateAction<boolean>>; } } | undefined;
88
- let notifyChange: (evt: NativeSyntheticEvent<TouchEvent>) => void | undefined;
89
+ let groupValue: { [key: string]: { checked: boolean; setValue: Dispatch<SetStateAction<boolean>>; } } | undefined
90
+ let notifyChange: (evt: NativeSyntheticEvent<TouchEvent>) => void | undefined
89
91
 
90
92
  const labelContext = useContext(LabelContext)
91
93
 
92
- const { textStyle, imageStyle, innerStyle } = splitStyle(style)
93
-
94
- if (imageStyle) {
95
- throwReactWarning('[Mpx runtime warn]: Radio does not support background image-related styles!')
96
- }
97
-
98
94
  const defaultStyle = {
99
95
  ...styles.wrapper,
100
96
  ...(isChecked && styles.wrapperChecked),
101
- ...(disabled && styles.wrapperDisabled),
97
+ ...(disabled && styles.wrapperDisabled)
102
98
  }
103
99
 
104
- const viewStyle = {
105
- ...defaultStyle,
106
- ...innerStyle
100
+ const styleObj = {
101
+ ...styles.container,
102
+ ...style
107
103
  }
108
104
 
109
105
  const onChange = (evt: NativeSyntheticEvent<TouchEvent>) => {
@@ -130,49 +126,27 @@ const Radio = forwardRef<HandlerRef<View, RadioProps>, RadioProps>(
130
126
  catchtap && catchtap(getCustomEvent('tap', evt, { layoutRef }, props))
131
127
  }
132
128
 
129
+ const {
130
+ hasSelfPercent,
131
+ normalStyle,
132
+ hasVarDec,
133
+ varContextRef,
134
+ setWidth,
135
+ setHeight
136
+ } = useTransformStyle(styleObj, { enableVar, externalVarContext, parentFontSize, parentWidth, parentHeight })
137
+
138
+ const { textStyle, backgroundStyle, innerStyle } = splitStyle(normalStyle)
139
+
140
+ if (backgroundStyle) {
141
+ warn('Radio does not support background image-related styles!')
142
+ }
143
+
133
144
  const { nodeRef } = useNodesRef(props, ref, {
134
145
  defaultStyle,
135
146
  change: onChange
136
147
  })
137
148
 
138
- const onLayout = () => {
139
- nodeRef.current?.measure(
140
- (
141
- x: number,
142
- y: number,
143
- width: number,
144
- height: number,
145
- offsetLeft: number,
146
- offsetTop: number
147
- ) => {
148
- layoutRef.current = { x, y, width, height, offsetLeft, offsetTop }
149
- }
150
- )
151
- }
152
-
153
- const wrapChildren = (
154
- children: ReactNode,
155
- textStyle?: TextStyle
156
- ) => {
157
- if (!children) return children
158
- const { textProps } = splitProps(props)
159
-
160
- if (every(children, (child) => isText(child))) {
161
- if (textStyle || textProps) {
162
- children = <Text key='radioTextWrap' style={textStyle || {}} {...(textProps || {})}>
163
- {children}
164
- </Text>
165
- }
166
- } else {
167
- if (textStyle) {
168
- throwReactWarning(
169
- '[Mpx runtime warn]: Text style will be ignored unless every child of the Radio is Text node!'
170
- )
171
- }
172
- }
173
-
174
- return children
175
- }
149
+ const { layoutRef, layoutStyle, layoutProps } = useLayout({ props, hasSelfPercent, setWidth, setHeight, nodeRef })
176
150
 
177
151
  if (groupContext) {
178
152
  groupValue = groupContext.groupValue
@@ -187,12 +161,12 @@ const Radio = forwardRef<HandlerRef<View, RadioProps>, RadioProps>(
187
161
  props,
188
162
  {
189
163
  ref: nodeRef,
190
- style: styles.container,
164
+ style: { ...innerStyle, ...layoutStyle },
165
+ ...layoutProps,
191
166
  bindtap: onTap,
192
- catchtap: catchTap,
193
- ...(enableOffset ? { onLayout } : {})
167
+ catchtap: catchTap
194
168
  },
195
- ['enable-offset'],
169
+ [],
196
170
  {
197
171
  layoutRef
198
172
  }
@@ -223,7 +197,7 @@ const Radio = forwardRef<HandlerRef<View, RadioProps>, RadioProps>(
223
197
 
224
198
  return (
225
199
  <View {...innerProps}>
226
- <View style={viewStyle}>
200
+ <View style={defaultStyle}>
227
201
  <Icon
228
202
  type='success'
229
203
  size={24}
@@ -235,7 +209,17 @@ const Radio = forwardRef<HandlerRef<View, RadioProps>, RadioProps>(
235
209
  }}
236
210
  />
237
211
  </View>
238
- {wrapChildren(children, textStyle)}
212
+ {
213
+ wrapChildren(
214
+ props,
215
+ {
216
+ hasVarDec,
217
+ varContext: varContextRef.current,
218
+ textStyle,
219
+ textProps
220
+ }
221
+ )
222
+ }
239
223
  </View>
240
224
  )
241
225
  }
@@ -3,23 +3,25 @@
3
3
  */
4
4
  import { ReactNode } from 'react'
5
5
  import { Portal } from '@ant-design/react-native'
6
-
6
+ import { warn } from '@mpxjs/utils'
7
7
  interface RootPortalProps {
8
8
  enable?: boolean
9
9
  children: ReactNode
10
+ [x: string]: any
10
11
  }
12
+
11
13
  const _RootPortal = (props: RootPortalProps) => {
12
14
  const { children, enable = true } = props
13
- return enable ? (
14
- // @ts-ignore
15
- <Portal>
15
+ if (props.style) {
16
+ warn('The root-portal component does not support the style prop.')
17
+ }
18
+ return enable
19
+ ? <Portal>
16
20
  {children}
17
21
  </Portal>
18
- ) : (
19
- <>{children}</>
20
- );
22
+ : <>{children}</>
21
23
  }
22
24
 
23
25
  _RootPortal.displayName = 'mpx-root-portal'
24
26
 
25
- export default _RootPortal
27
+ export default _RootPortal