@mpxjs/webpack-plugin 2.9.70-alpha.0 → 2.9.71

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 (126) hide show
  1. package/LICENSE +433 -0
  2. package/README.md +1 -1
  3. package/lib/config.js +0 -14
  4. package/lib/dependencies/ResolveDependency.js +0 -5
  5. package/lib/index.js +7 -38
  6. package/lib/json-compiler/helper.js +3 -3
  7. package/lib/loader.js +0 -53
  8. package/lib/parser.js +1 -1
  9. package/lib/platform/json/wx/index.js +21 -8
  10. package/lib/platform/style/wx/index.js +51 -54
  11. package/lib/platform/template/wx/component-config/button.js +2 -14
  12. package/lib/platform/template/wx/component-config/fix-component-name.js +15 -12
  13. package/lib/platform/template/wx/component-config/image.js +0 -4
  14. package/lib/platform/template/wx/component-config/index.js +1 -1
  15. package/lib/platform/template/wx/component-config/input.js +0 -4
  16. package/lib/platform/template/wx/component-config/movable-view.js +8 -1
  17. package/lib/platform/template/wx/component-config/picker-view.js +1 -5
  18. package/lib/platform/template/wx/component-config/rich-text.js +6 -2
  19. package/lib/platform/template/wx/component-config/scroll-view.js +1 -5
  20. package/lib/platform/template/wx/component-config/switch.js +0 -4
  21. package/lib/platform/template/wx/component-config/text.js +0 -4
  22. package/lib/platform/template/wx/component-config/textarea.js +0 -5
  23. package/lib/platform/template/wx/component-config/unsupported.js +1 -1
  24. package/lib/platform/template/wx/component-config/view.js +0 -4
  25. package/lib/platform/template/wx/index.js +1 -131
  26. package/lib/resolve-loader.js +1 -4
  27. package/lib/runtime/components/react/context.ts +8 -0
  28. package/lib/runtime/components/react/dist/context.js +2 -0
  29. package/lib/runtime/components/react/dist/getInnerListeners.js +39 -37
  30. package/lib/runtime/components/react/dist/mpx-button.jsx +16 -44
  31. package/lib/runtime/components/react/dist/mpx-canvas/html.js +2 -4
  32. package/lib/runtime/components/react/dist/mpx-canvas/index.jsx +5 -1
  33. package/lib/runtime/components/react/dist/mpx-movable-view.jsx +93 -58
  34. package/lib/runtime/components/react/dist/mpx-navigator.jsx +1 -1
  35. package/lib/runtime/components/react/dist/mpx-picker-view-column-item.jsx +10 -14
  36. package/lib/runtime/components/react/dist/mpx-picker-view-column.jsx +94 -81
  37. package/lib/runtime/components/react/dist/mpx-picker-view.jsx +19 -16
  38. package/lib/runtime/components/react/dist/mpx-rich-text/index.jsx +10 -11
  39. package/lib/runtime/components/react/dist/mpx-scroll-view.jsx +11 -4
  40. package/lib/runtime/components/react/dist/mpx-swiper-item.jsx +31 -8
  41. package/lib/runtime/components/react/dist/mpx-swiper.jsx +435 -371
  42. package/lib/runtime/components/react/dist/mpx-view.jsx +18 -53
  43. package/lib/runtime/components/react/dist/pickerFaces.js +3 -8
  44. package/lib/runtime/components/react/dist/pickerVIewContext.js +5 -0
  45. package/lib/runtime/components/react/dist/{pickerViewOverlay.jsx → pickerViewIndicator.jsx} +6 -6
  46. package/lib/runtime/components/react/dist/pickerViewMask.jsx +2 -2
  47. package/lib/runtime/components/react/dist/useAnimationHooks.js +27 -10
  48. package/lib/runtime/components/react/dist/utils.jsx +162 -70
  49. package/lib/runtime/components/react/event.config.ts +25 -26
  50. package/lib/runtime/components/react/getInnerListeners.ts +236 -182
  51. package/lib/runtime/components/react/mpx-button.tsx +27 -69
  52. package/lib/runtime/components/react/mpx-canvas/html.ts +2 -4
  53. package/lib/runtime/components/react/mpx-canvas/index.tsx +44 -46
  54. package/lib/runtime/components/react/mpx-checkbox-group.tsx +15 -13
  55. package/lib/runtime/components/react/mpx-checkbox.tsx +20 -21
  56. package/lib/runtime/components/react/mpx-form.tsx +15 -20
  57. package/lib/runtime/components/react/mpx-icon.tsx +2 -2
  58. package/lib/runtime/components/react/mpx-image.tsx +87 -47
  59. package/lib/runtime/components/react/mpx-input.tsx +24 -32
  60. package/lib/runtime/components/react/mpx-label.tsx +12 -14
  61. package/lib/runtime/components/react/mpx-movable-area.tsx +10 -16
  62. package/lib/runtime/components/react/mpx-movable-view.tsx +133 -92
  63. package/lib/runtime/components/react/mpx-navigator.tsx +3 -9
  64. package/lib/runtime/components/react/mpx-picker-view-column-item.tsx +76 -0
  65. package/lib/runtime/components/react/mpx-picker-view-column.tsx +206 -183
  66. package/lib/runtime/components/react/mpx-picker-view.tsx +49 -48
  67. package/lib/runtime/components/react/mpx-radio-group.tsx +13 -15
  68. package/lib/runtime/components/react/mpx-radio.tsx +19 -25
  69. package/lib/runtime/components/react/mpx-rich-text/html.ts +40 -0
  70. package/lib/runtime/components/react/mpx-rich-text/index.tsx +115 -0
  71. package/lib/runtime/components/react/mpx-root-portal.tsx +3 -5
  72. package/lib/runtime/components/react/mpx-scroll-view.tsx +53 -43
  73. package/lib/runtime/components/react/mpx-swiper-item.tsx +45 -11
  74. package/lib/runtime/components/react/mpx-swiper.tsx +742 -0
  75. package/lib/runtime/components/react/mpx-switch.tsx +19 -15
  76. package/lib/runtime/components/react/mpx-text.tsx +8 -16
  77. package/lib/runtime/components/react/mpx-textarea.tsx +11 -10
  78. package/lib/runtime/components/react/mpx-view.tsx +28 -77
  79. package/lib/runtime/components/react/mpx-web-view.tsx +94 -59
  80. package/lib/runtime/components/react/pickerFaces.ts +10 -7
  81. package/lib/runtime/components/react/pickerVIewContext.ts +27 -0
  82. package/lib/runtime/components/react/pickerViewIndicator.tsx +34 -0
  83. package/lib/runtime/components/react/pickerViewMask.tsx +30 -0
  84. package/lib/runtime/components/react/types/{getInnerListeners.ts → getInnerListeners.d.ts} +4 -5
  85. package/lib/runtime/components/react/types/global.d.ts +12 -1
  86. package/lib/runtime/components/react/useAnimationHooks.ts +60 -15
  87. package/lib/runtime/components/react/utils.tsx +175 -71
  88. package/lib/runtime/components/web/mpx-checkbox.vue +1 -1
  89. package/lib/runtime/components/web/mpx-picker-view-column.vue +9 -4
  90. package/lib/runtime/components/web/mpx-web-view.vue +34 -20
  91. package/lib/runtime/optionProcessor.js +0 -22
  92. package/lib/style-compiler/index.js +1 -1
  93. package/lib/style-compiler/plugins/scope-id.js +30 -2
  94. package/lib/template-compiler/compiler.js +91 -39
  95. package/lib/utils/env.js +1 -6
  96. package/lib/utils/pre-process-json.js +9 -5
  97. package/lib/wxss/loader.js +15 -2
  98. package/package.json +4 -7
  99. package/lib/dependencies/AddEntryDependency.js +0 -24
  100. package/lib/runtime/components/react/dist/types/common.js +0 -1
  101. package/lib/runtime/components/react/dist/types/getInnerListeners.js +0 -1
  102. package/lib/runtime/components/react/mpx-swiper/carouse.tsx +0 -527
  103. package/lib/runtime/components/react/mpx-swiper/index.tsx +0 -80
  104. package/lib/runtime/components/react/mpx-swiper/type.ts +0 -87
  105. package/lib/runtime/components/react/pickerOverlay.tsx +0 -32
  106. package/lib/runtime/components/tenon/getInnerListeners.js +0 -334
  107. package/lib/runtime/components/tenon/tenon-button.vue +0 -309
  108. package/lib/runtime/components/tenon/tenon-image.vue +0 -66
  109. package/lib/runtime/components/tenon/tenon-input.vue +0 -171
  110. package/lib/runtime/components/tenon/tenon-rich-text.vue +0 -26
  111. package/lib/runtime/components/tenon/tenon-scroll-view.vue +0 -127
  112. package/lib/runtime/components/tenon/tenon-switch.vue +0 -96
  113. package/lib/runtime/components/tenon/tenon-text.vue +0 -70
  114. package/lib/runtime/components/tenon/tenon-textarea.vue +0 -86
  115. package/lib/runtime/components/tenon/tenon-view.vue +0 -93
  116. package/lib/runtime/components/web/event.js +0 -105
  117. package/lib/runtime/optionProcessor.tenon.js +0 -84
  118. package/lib/style-compiler/plugins/hm.js +0 -20
  119. package/lib/tenon/index.js +0 -117
  120. package/lib/tenon/processJSON.js +0 -352
  121. package/lib/tenon/processScript.js +0 -203
  122. package/lib/tenon/processStyles.js +0 -21
  123. package/lib/tenon/processTemplate.js +0 -126
  124. package/lib/tenon/script-helper.js +0 -223
  125. package/lib/utils/get-relative-path.js +0 -25
  126. /package/lib/runtime/components/react/types/{common.ts → common.d.ts} +0 -0
@@ -1,5 +1,5 @@
1
1
  import { View } from 'react-native'
2
- import React, { forwardRef, useState, useRef } from 'react'
2
+ import React, { forwardRef, useRef } from 'react'
3
3
  import useInnerProps, { getCustomEvent } from './getInnerListeners'
4
4
  import useNodesRef, { HandlerRef } from './useNodesRef'
5
5
  import {
@@ -7,35 +7,33 @@ import {
7
7
  splitProps,
8
8
  splitStyle,
9
9
  wrapChildren,
10
- parseInlineStyle,
11
10
  useTransformStyle,
12
- useDebounceCallback,
13
- useStableCallback,
14
11
  extendObject
15
12
  } from './utils'
13
+ import { PickerViewStyleContext } from './pickerVIewContext'
16
14
  import type { AnyFunc } from './types/common'
17
15
  /**
18
16
  * ✔ value
19
17
  * ✔ bindchange
20
18
  * ✘ bindpickstart
21
19
  * ✘ bindpickend
22
- * mask-class
20
+ * mask-class
23
21
  * ✔ indicator-style: 优先级indicator-style.height > pick-view-column中的子元素设置的height
24
- * indicator-class
25
- * mask-style
22
+ * WebView Only:
23
+ * indicator-class
24
+ * ✔ mask-style
26
25
  * ✘ immediate-change
27
26
  */
28
27
 
29
28
  interface PickerViewProps {
30
29
  children: React.ReactNode
31
- // 初始的defaultValue数组中的数字依次表示 picker-view 内的 picker-view-column 选择的第几项(下标从 0 开始),
32
- // 数字大于 picker-view-column 可选项长度时,选择最后一项。
33
30
  value?: Array<number>
34
31
  bindchange?: AnyFunc
35
32
  style: {
36
33
  [key: string]: any
37
34
  }
38
- 'indicator-style'?: string
35
+ 'indicator-style'?: Record<string, any>,
36
+ 'mask-style'?: Record<string, any>,
39
37
  'enable-var': boolean
40
38
  'external-var-context'?: Record<string, any>,
41
39
  'enable-offset': boolean
@@ -62,25 +60,25 @@ const styles: { [key: string]: Object } = {
62
60
  }
63
61
  }
64
62
 
63
+ const DefaultPickerItemH = 36
64
+
65
65
  const _PickerView = forwardRef<HandlerRef<View, PickerViewProps>, PickerViewProps>((props: PickerViewProps, ref) => {
66
66
  const {
67
67
  children,
68
68
  value = [],
69
69
  bindchange,
70
70
  style,
71
+ 'indicator-style': indicatorStyle = {},
72
+ 'mask-style': pickerMaskStyle = {},
71
73
  'enable-var': enableVar,
72
74
  'external-var-context': externalVarContext
73
75
  } = props
74
-
75
- // indicatorStyle 需要转换为rn的style
76
- // 微信设置到pick-view上上设置的normalStyle如border等需要转换成RN的style然后进行透传
77
- const indicatorStyle = parseInlineStyle(props['indicator-style'])
78
- const { height: indicatorH, ...pickerOverlayStyle } = indicatorStyle
79
- const [pickMaxH, setPickMaxH] = useState(0)
76
+ const { height: indicatorH, ...pickerIndicatorStyle } = indicatorStyle
80
77
  const nodeRef = useRef(null)
81
78
  const cloneRef = useRef(null)
82
79
  const activeValueRef = useRef(value)
83
80
  activeValueRef.current = value.slice()
81
+ const snapActiveValueRef = useRef<number[] | null>(null)
84
82
 
85
83
  const {
86
84
  normalStyle,
@@ -96,7 +94,6 @@ const _PickerView = forwardRef<HandlerRef<View, PickerViewProps>, PickerViewProp
96
94
  })
97
95
 
98
96
  const {
99
- // 存储layout布局信息
100
97
  layoutRef,
101
98
  layoutProps,
102
99
  layoutStyle
@@ -104,33 +101,32 @@ const _PickerView = forwardRef<HandlerRef<View, PickerViewProps>, PickerViewProp
104
101
  const { textProps } = splitProps(props)
105
102
  const { textStyle } = splitStyle(normalStyle)
106
103
 
107
- const onColumnItemRawHChange = (height: number) => {
108
- if (height > pickMaxH) {
109
- setPickMaxH(height)
110
- }
111
- }
112
-
113
- const bindchangeDebounce = useDebounceCallback(useStableCallback(bindchange), 300)
114
-
115
104
  const onSelectChange = (columnIndex: number, selectedIndex: number) => {
116
- bindchangeDebounce.clear()
117
105
  const activeValue = activeValueRef.current
118
106
  activeValue[columnIndex] = selectedIndex
119
107
  const eventData = getCustomEvent(
120
108
  'change',
121
109
  {},
122
- { detail: { value: activeValue, source: 'change' }, layoutRef }
110
+ { detail: { value: activeValue.slice(), source: 'change' }, layoutRef }
123
111
  )
124
- bindchangeDebounce(eventData)
112
+ bindchange?.(eventData)
113
+ snapActiveValueRef.current = activeValueRef.current
125
114
  }
126
115
 
127
- const onInitialChange = (value: number[]) => {
128
- const eventData = getCustomEvent(
129
- 'change',
130
- {},
131
- { detail: { value, source: 'change' }, layoutRef }
132
- )
133
- bindchange?.(eventData) // immediate
116
+ const hasDiff = (a: number[] = [], b: number[]) => {
117
+ return a.some((v, i) => v !== b[i])
118
+ }
119
+
120
+ const onInitialChange = (isInvalid: boolean, value: number[]) => {
121
+ if (isInvalid || !snapActiveValueRef.current || hasDiff(snapActiveValueRef.current, value)) {
122
+ const eventData = getCustomEvent(
123
+ 'change',
124
+ {},
125
+ { detail: { value: value.slice(), source: 'change' }, layoutRef }
126
+ )
127
+ bindchange?.(eventData)
128
+ snapActiveValueRef.current = value.slice()
129
+ }
134
130
  }
135
131
 
136
132
  const innerProps = useInnerProps(
@@ -148,12 +144,17 @@ const _PickerView = forwardRef<HandlerRef<View, PickerViewProps>, PickerViewProp
148
144
  ),
149
145
  layoutProps
150
146
  }),
151
- ['enable-offset'],
147
+ [
148
+ 'enable-offset',
149
+ 'indicator-style',
150
+ 'indicator-class',
151
+ 'mask-style',
152
+ 'mask-class'
153
+ ],
152
154
  { layoutRef }
153
155
  )
154
156
 
155
157
  const renderColumn = (child: React.ReactElement, index: number, columnData: React.ReactNode[], initialIndex: number) => {
156
- const extraProps = {}
157
158
  const childProps = child?.props || {}
158
159
  const wrappedProps = extendObject(
159
160
  {},
@@ -164,15 +165,14 @@ const _PickerView = forwardRef<HandlerRef<View, PickerViewProps>, PickerViewProp
164
165
  columnIndex: index,
165
166
  key: `pick-view-${index}`,
166
167
  wrapperStyle: {
167
- height: normalStyle?.height || 0,
168
- itemHeight: indicatorH || 0
168
+ height: normalStyle?.height || DefaultPickerItemH,
169
+ itemHeight: indicatorH || DefaultPickerItemH
169
170
  },
170
- onColumnItemRawHChange,
171
171
  onSelectChange: onSelectChange.bind(null, index),
172
172
  initialIndex,
173
- pickerOverlayStyle
174
- },
175
- extraProps
173
+ pickerIndicatorStyle,
174
+ pickerMaskStyle
175
+ }
176
176
  )
177
177
  const realElement = React.cloneElement(child, wrappedProps)
178
178
  return wrapChildren(
@@ -215,17 +215,18 @@ const _PickerView = forwardRef<HandlerRef<View, PickerViewProps>, PickerViewProp
215
215
  validValue.push(validIndex)
216
216
  renderColumns.push(renderColumn(item, index, columnData, validIndex))
217
217
  })
218
- isInvalid && onInitialChange(validValue)
218
+ onInitialChange(isInvalid, validValue)
219
219
  return renderColumns
220
220
  }
221
221
 
222
222
  return (
223
- <View {...innerProps}>
224
- <View style={[styles.wrapper]}>{renderPickerColumns()}</View>
225
- </View>
223
+ <PickerViewStyleContext.Provider value={textStyle}>
224
+ <View {...innerProps}>
225
+ <View style={[styles.wrapper]}>{renderPickerColumns()}</View>
226
+ </View>
227
+ </PickerViewStyleContext.Provider>
226
228
  )
227
229
  })
228
230
 
229
231
  _PickerView.displayName = 'MpxPickerView'
230
-
231
232
  export default _PickerView
@@ -8,7 +8,8 @@ import {
8
8
  ReactNode,
9
9
  useContext,
10
10
  useMemo,
11
- useEffect
11
+ useEffect,
12
+ createElement
12
13
  } from 'react'
13
14
  import {
14
15
  View,
@@ -154,20 +155,17 @@ const radioGroup = forwardRef<
154
155
  }
155
156
  )
156
157
 
157
- return (
158
- <View {...innerProps}>
159
- <RadioGroupContext.Provider value={contextValue}>
160
- {
161
- wrapChildren(
162
- props,
163
- {
164
- hasVarDec,
165
- varContext: varContextRef.current
166
- }
167
- )
168
- }
169
- </RadioGroupContext.Provider>
170
- </View>
158
+ return createElement(View, innerProps, createElement(
159
+ RadioGroupContext.Provider,
160
+ { value: contextValue },
161
+ wrapChildren(
162
+ props,
163
+ {
164
+ hasVarDec,
165
+ varContext: varContextRef.current
166
+ }
167
+ )
168
+ )
171
169
  )
172
170
  })
173
171
 
@@ -4,7 +4,7 @@
4
4
  * ✔ checked
5
5
  * ✔ color
6
6
  */
7
- import { JSX, useRef, useState, forwardRef, useEffect, ReactNode, useContext, Dispatch, SetStateAction } from 'react'
7
+ import { JSX, useRef, useState, forwardRef, useEffect, ReactNode, useContext, Dispatch, SetStateAction, createElement } from 'react'
8
8
  import { View, StyleSheet, ViewStyle, NativeSyntheticEvent } from 'react-native'
9
9
  import { warn } from '@mpxjs/utils'
10
10
  import { LabelContext, RadioGroupContext } from './context'
@@ -193,32 +193,26 @@ const Radio = forwardRef<HandlerRef<View, RadioProps>, RadioProps>(
193
193
  }
194
194
  }, [checked])
195
195
 
196
- return (
197
- <View {...innerProps}>
198
- <View style={defaultStyle}>
199
- <Icon
200
- type='success'
201
- size={24}
202
- color={disabled ? '#E1E1E1' : color}
203
- style={{
204
- ...styles.icon,
205
- ...(isChecked && styles.iconChecked),
206
- ...(disabled && styles.iconDisabled)
207
- }}
208
- />
209
- </View>
196
+ return createElement(View, innerProps,
197
+ createElement(
198
+ View,
199
+ { style: defaultStyle },
200
+ createElement(Icon, {
201
+ type: 'success',
202
+ size: 24,
203
+ color: disabled ? '#E1E1E1' : color,
204
+ style: extendObject({}, styles.icon, isChecked && styles.iconChecked, disabled && styles.iconDisabled)
205
+ })
206
+ ),
207
+ wrapChildren(
208
+ props,
210
209
  {
211
- wrapChildren(
212
- props,
213
- {
214
- hasVarDec,
215
- varContext: varContextRef.current,
216
- textStyle,
217
- textProps
218
- }
219
- )
210
+ hasVarDec,
211
+ varContext: varContextRef.current,
212
+ textStyle,
213
+ textProps
220
214
  }
221
- </View>
215
+ )
222
216
  )
223
217
  }
224
218
  )
@@ -0,0 +1,40 @@
1
+
2
+ export const generateHTML = (html: string) => {
3
+ return `<html><head>
4
+ <meta content="width=device-width, initial-scale=1, maximum-scale=1, user-scaleable=no" name="viewport">
5
+ <style>
6
+ html {
7
+ -ms-content-zooming: none;
8
+ -ms-touch-action: pan-x pan-y;
9
+ }
10
+ body {
11
+ position: fixed;
12
+ top: 0;
13
+ right: 0;
14
+ bottom: 0;
15
+ left: 0;
16
+ overflow: hidden;
17
+ }
18
+ html,body {
19
+ margin: 0;
20
+ padding: 0;
21
+ }
22
+ * {
23
+ user-select: none;
24
+ -ms-user-select: none;
25
+ -moz-user-select: none;
26
+ -webkit-user-select: none;
27
+ }
28
+ </style>
29
+ </head>
30
+ <body><div id="rich-text">${html}</div>
31
+ <script>
32
+ function sendHeight() {
33
+ const dom = document.getElementById('rich-text')
34
+ window.ReactNativeWebView.postMessage(dom.scrollHeight);
35
+ }
36
+ window.onload = sendHeight;
37
+ </script>
38
+ </body
39
+ ></html>`
40
+ }
@@ -0,0 +1,115 @@
1
+
2
+ /**
3
+ * ✔ nodes
4
+ */
5
+ import { View, ViewProps, ViewStyle } from 'react-native'
6
+ import { useRef, forwardRef, JSX, useState, createElement } from 'react'
7
+ import useInnerProps from '../getInnerListeners'
8
+ import useNodesRef, { HandlerRef } from '../useNodesRef' // 引入辅助函数
9
+ import { useTransformStyle, useLayout, extendObject } from '../utils'
10
+ import { WebView, WebViewMessageEvent } from 'react-native-webview'
11
+ import { generateHTML } from './html'
12
+
13
+ type Node = {
14
+ type: 'node' | 'text'
15
+ name?: string
16
+ attrs?: any
17
+ children?: Array<Node>
18
+ text: string
19
+ }
20
+
21
+ interface _RichTextProps extends ViewProps {
22
+ style?: ViewStyle
23
+ nodes: string | Array<Node>
24
+ 'enable-var'?: boolean
25
+ 'external-var-context'?: Record<string, any>
26
+ 'parent-font-size'?: number
27
+ 'parent-width'?: number
28
+ 'parent-height'?: number
29
+ }
30
+
31
+ function jsonToHtmlStr (elements: Array<Node>) {
32
+ let htmlStr = ''
33
+
34
+ for (const element of elements) {
35
+ if (element.type === 'text') {
36
+ htmlStr += element.text
37
+ return htmlStr
38
+ }
39
+
40
+ const { name, attrs = {}, children = [] } = element
41
+
42
+ let attrStr = ''
43
+ for (const [key, value] of Object.entries(attrs)) attrStr += ` ${key}="${value}"`
44
+
45
+ let childrenStr = ''
46
+ for (const child of children) childrenStr += jsonToHtmlStr([child])
47
+
48
+ htmlStr += `<${name}${attrStr}>${childrenStr}</${name}>`
49
+ }
50
+
51
+ return htmlStr
52
+ }
53
+
54
+ const _RichText = forwardRef<HandlerRef<View, _RichTextProps>, _RichTextProps>((props, ref): JSX.Element => {
55
+ const {
56
+ style = {},
57
+ nodes,
58
+ 'enable-var': enableVar,
59
+ 'external-var-context': externalVarContext,
60
+ 'parent-font-size': parentFontSize,
61
+ 'parent-width': parentWidth,
62
+ 'parent-height': parentHeight
63
+ } = props
64
+
65
+ const nodeRef = useRef(null)
66
+ const [webViewHeight, setWebViewHeight] = useState(0)
67
+
68
+ const {
69
+ normalStyle,
70
+ hasSelfPercent,
71
+ setWidth,
72
+ setHeight
73
+ } = useTransformStyle(Object.assign({
74
+ width: '100%',
75
+ height: webViewHeight
76
+ }, style), {
77
+ enableVar,
78
+ externalVarContext,
79
+ parentFontSize,
80
+ parentWidth,
81
+ parentHeight
82
+ })
83
+
84
+ const {
85
+ layoutRef,
86
+ layoutStyle,
87
+ layoutProps
88
+ } = useLayout({ props, hasSelfPercent, setWidth, setHeight, nodeRef })
89
+
90
+ useNodesRef<View, _RichTextProps>(props, ref, nodeRef, {
91
+ layoutRef
92
+ })
93
+
94
+ const innerProps = useInnerProps(props, extendObject({
95
+ ref: nodeRef,
96
+ style: extendObject(normalStyle, layoutStyle)
97
+ }, layoutProps), [], {
98
+ layoutRef
99
+ })
100
+
101
+ const html: string = typeof nodes === 'string' ? nodes : jsonToHtmlStr(nodes)
102
+
103
+ return createElement(View, innerProps,
104
+ createElement(WebView, {
105
+ source: { html: generateHTML(html) },
106
+ onMessage: (event: WebViewMessageEvent) => {
107
+ setWebViewHeight(+event.nativeEvent.data)
108
+ }
109
+ })
110
+ )
111
+ })
112
+
113
+ _RichText.displayName = 'mpx-rich-text'
114
+
115
+ export default _RichText
@@ -1,7 +1,7 @@
1
1
  /**
2
2
  * ✔ enable
3
3
  */
4
- import { ReactNode } from 'react'
4
+ import { ReactNode, createElement, Fragment } from 'react'
5
5
  import { Portal } from '@ant-design/react-native'
6
6
  import { warn } from '@mpxjs/utils'
7
7
  interface RootPortalProps {
@@ -16,10 +16,8 @@ const _RootPortal = (props: RootPortalProps) => {
16
16
  warn('The root-portal component does not support the style prop.')
17
17
  }
18
18
  return enable
19
- ? <Portal>
20
- {children}
21
- </Portal>
22
- : <>{children}</>
19
+ ? createElement(Portal, null, children)
20
+ : createElement(Fragment, null, children)
23
21
  }
24
22
 
25
23
  _RootPortal.displayName = 'MpxRootPortal'
@@ -33,13 +33,13 @@
33
33
  */
34
34
  import { ScrollView } from 'react-native-gesture-handler'
35
35
  import { View, RefreshControl, NativeSyntheticEvent, NativeScrollEvent, LayoutChangeEvent, ViewStyle } from 'react-native'
36
- import { JSX, ReactNode, RefObject, useRef, useState, useEffect, forwardRef, useContext } from 'react'
36
+ import { JSX, ReactNode, RefObject, useRef, useState, useEffect, forwardRef, useContext, createElement, useMemo } from 'react'
37
37
  import { useAnimatedRef } from 'react-native-reanimated'
38
38
  import { warn } from '@mpxjs/utils'
39
39
  import useInnerProps, { getCustomEvent } from './getInnerListeners'
40
40
  import useNodesRef, { HandlerRef } from './useNodesRef'
41
41
  import { splitProps, splitStyle, useTransformStyle, useLayout, wrapChildren, extendObject, flatGesture, GestureHandler } from './utils'
42
- import { IntersectionObserverContext } from './context'
42
+ import { IntersectionObserverContext, ScrollViewContext } from './context'
43
43
 
44
44
  interface ScrollViewProps {
45
45
  children?: ReactNode;
@@ -165,7 +165,7 @@ const _ScrollView = forwardRef<HandlerRef<ScrollView & View, ScrollViewProps>, S
165
165
  const initialTimeout = useRef<ReturnType<typeof setTimeout> | null>(null)
166
166
  const intersectionObservers = useContext(IntersectionObserverContext)
167
167
 
168
- const snapScrollIntoView = useRef<string>('')
168
+ const firstScrollIntoViewChange = useRef<boolean>(false)
169
169
 
170
170
  const {
171
171
  normalStyle,
@@ -194,6 +194,12 @@ const _ScrollView = forwardRef<HandlerRef<ScrollView & View, ScrollViewProps>, S
194
194
  gestureRef: scrollViewRef
195
195
  })
196
196
 
197
+ const contextValue = useMemo(() => {
198
+ return {
199
+ gestureRef: scrollViewRef
200
+ }
201
+ }, [])
202
+
197
203
  const { layoutRef, layoutStyle, layoutProps } = useLayout({ props, hasSelfPercent, setWidth, setHeight, nodeRef: scrollViewRef, onLayout })
198
204
 
199
205
  if (scrollX && scrollY) {
@@ -220,23 +226,28 @@ const _ScrollView = forwardRef<HandlerRef<ScrollView & View, ScrollViewProps>, S
220
226
  }, [refresherTriggered])
221
227
 
222
228
  useEffect(() => {
223
- if (scrollIntoView && __selectRef && snapScrollIntoView.current !== scrollIntoView) {
224
- snapScrollIntoView.current = scrollIntoView || ''
225
- setTimeout(() => {
226
- const refs = __selectRef(`#${scrollIntoView}`, 'node')
227
- if (refs) {
228
- const { nodeRef } = refs.getNodeInstance()
229
- nodeRef.current?.measureLayout(
230
- scrollViewRef.current,
231
- (left: number, top:number) => {
232
- scrollToOffset(left, top)
233
- }
234
- )
235
- }
236
- })
229
+ if (scrollIntoView && __selectRef) {
230
+ if (!firstScrollIntoViewChange.current) {
231
+ setTimeout(handleScrollIntoView)
232
+ } else {
233
+ handleScrollIntoView()
234
+ }
237
235
  }
236
+ firstScrollIntoViewChange.current = true
238
237
  }, [scrollIntoView])
239
238
 
239
+ function handleScrollIntoView () {
240
+ const refs = __selectRef!(`#${scrollIntoView}`, 'node')
241
+ if (!refs) return
242
+ const { nodeRef } = refs.getNodeInstance()
243
+ nodeRef.current?.measureLayout(
244
+ scrollViewRef.current,
245
+ (left: number, top:number) => {
246
+ scrollToOffset(left, top)
247
+ }
248
+ )
249
+ }
250
+
240
251
  function selectLength (size: { height: number; width: number }) {
241
252
  return !scrollX ? size.height : size.width
242
253
  }
@@ -327,6 +338,8 @@ const _ScrollView = forwardRef<HandlerRef<ScrollView & View, ScrollViewProps>, S
327
338
  }, props)
328
339
  )
329
340
  updateScrollOptions(e, { scrollLeft, scrollTop })
341
+ onStartReached(e)
342
+ onEndReached(e)
330
343
  if (enableTriggerIntersectionObserver && intersectionObservers) {
331
344
  for (const key in intersectionObservers) {
332
345
  intersectionObservers[key].throttleMeasure()
@@ -491,32 +504,29 @@ const _ScrollView = forwardRef<HandlerRef<ScrollView & View, ScrollViewProps>, S
491
504
  white: ['#fff']
492
505
  }
493
506
 
494
- return (
495
- <ScrollView
496
- {...innerProps}
497
- refreshControl={refresherEnabled
498
- ? (
499
- <RefreshControl
500
- progressBackgroundColor={refresherBackground}
501
- refreshing={refreshing}
502
- onRefresh={onRefresh}
503
- {...(refresherDefaultStyle && refresherDefaultStyle !== 'none' ? { colors: refreshColor[refresherDefaultStyle] } : {})}
504
- />
505
- )
506
- : undefined}
507
- >
508
- {
509
- wrapChildren(
510
- props,
511
- {
512
- hasVarDec,
513
- varContext: varContextRef.current,
514
- textStyle,
515
- textProps
516
- }
517
- )
518
- }
519
- </ScrollView>
507
+ return createElement(
508
+ ScrollView,
509
+ extendObject({}, innerProps, {
510
+ refreshControl: refresherEnabled
511
+ ? createElement(RefreshControl, extendObject({
512
+ progressBackgroundColor: refresherBackground,
513
+ refreshing: refreshing,
514
+ onRefresh: onRefresh
515
+ }, (refresherDefaultStyle && refresherDefaultStyle !== 'none' ? { colors: refreshColor[refresherDefaultStyle] } : null)))
516
+ : undefined
517
+ }),
518
+ createElement(ScrollViewContext.Provider,
519
+ { value: contextValue },
520
+ wrapChildren(
521
+ props,
522
+ {
523
+ hasVarDec,
524
+ varContext: varContextRef.current,
525
+ textStyle,
526
+ textProps
527
+ }
528
+ )
529
+ )
520
530
  )
521
531
  })
522
532