双线程的 React
如果无法正常显示,请先停止浏览器的去广告插件。
1. 双线程的 React
Lynx 团队
蚂蚁终端体验科技大会
2.
3. Xuan Huang (
) / @huxpro
4. 2025 年,已经有很多前端/终端 程师投身于 AI Coding、Agent 程、数据 程、具身
智能等领域,变的是每天写的代码和交付的产物,不变的是他们仍然是每个项 组 最
懂产品和 户体验的那帮 。
5 年前,偏右在做 Ant Design,现在他在探索 AI 程和前端的职责边界。他将在 SEE
Conf 2025 分享《AI for Frontend》。
5 年前,达峰在做语雀,现在他在打造体验技术的智能引擎,他将分享实践思考。
5 年前,阿 在做前端 程化和 DevOps,现在他在阿 云做 Qoder。他将在 SEE Conf
2025 分享《我,前端,AI》。
5 年前,
在做 React Native,现在他在字节 Lynx 继续深耕跨端技术。他将在 SEE
Conf 2025 分享《双线程的 React》。
5 年前,闻冰在搞 D2C 和设计 程化,现在他的 LobeHub 是最流 的开源 AI 效能 具
之 。他将在 SEE Conf 2025 分享《AI Coding 与开源协作的新范式》。
5. 2025 年,已经有很多前端/终端 程师投身于 AI Coding、Agent 程、数据 程、具身
智能等领域,变的是每天写的代码和交付的产物,不变的是他们仍然是每个项 组 最
懂产品和 户体验的那帮 。
5 年前,偏右在做 Ant Design,现在他在探索 AI 程和前端的职责边界。他将在 SEE
Conf 2025 分享《AI for Frontend》。
5 年前,达峰在做语雀,现在他在打造体验技术的智能引擎,他将分享实践思考。
5 年前,阿 在做前端 程化和 DevOps,现在他在阿 云做 Qoder。他将在 SEE Conf
2025 分享《我,前端,AI》。
5 年前,
在做 React Native,现在他在字节 Lynx 继续深耕跨端技术。他将在 SEE
Conf 2025 分享《双线程的 React》。
5 年前,闻冰在搞 D2C 和设计 程化,现在他的 LobeHub 是最流 的开源 AI 效能 具
之 。他将在 SEE Conf 2025 分享《AI Coding 与开源协作的新范式》。
6. 5 年前,达峰在做语雀,现在他在打造体验技术的智能引擎,他将分享实践思考。
5 年前,阿 在做前端 程化和 DevOps,现在他在阿 云做 Qoder。他将在 SEE Conf
2025 分享《我,前端,AI》。
5 年前,
在做 React Native,现在他在字节 Lynx 继续深耕跨端技术。他将在 SEE
Conf 2025 分享《双线程的 React》。
5 年前,闻冰在搞 D2C 和设计 程化,现在他的 LobeHub 是最流 的开源 AI 效能 具
之 。他将在 SEE Conf 2025 分享《AI Coding 与开源协作的新范式》。
程实践的坚守者,想寻找古法前端的意义和价值,来杭州,来
如果你是 户体验和
SEE Conf!
7. 古法前端
GUI
React
Web
8. 现代前端
GUI
React
Web
AI
9.
10. Event
UI
Update
11. Event
Event
Event
UI
Update
Update
Update
12. Event
UI
Update
13. Frame
Main
Event
JavaScript
Paint
14. Expensive Rendering
Frame
Main
Event
React
Paint
15. Web
Paint Control
Frame
Frame
Main
Event
React
Paint
Event
React
Frame Control
Paint
16. Mobile
Frame
Main
Event
Native UI
Paint
17. Mobile
Frame
Main
Event
JavaScript
Native UI
Paint
18. Frame
Main
Event
React
Native UI
Paint
19. Frame
Main
Background
Event
Native UI
React
Paint
20. Paper
Frame
Main
Background
Event
Native UI
Paint
React
Native UI
Paint
21. Paint Control
Frame
Main
Background
Event
Native UI
Paint
Native UI
React
Frame Control
Non-Blocking
Paint
22. Fabric
Frame
Main
Background
Event
Native Renderer
React
Native UI
Paint
23. Web
Fabric
Paper
Sync
Async
24. Web
Paper
Lynx
Fabric
Sync
Async
25. Sync
Background
React
Async
26. Main
Background
JavaScriptSync
ReactAsync
27. MainReactSync
BackgroundReactAsync
28. Ziqi Zhen (甄
琦) / @Yradex
29. function Slider({ min, max, initialValue, onChange }) {
const [value, setValue] = useState(initialValue);
const ratio = valueToRatio(value, min, max);
return (
<view> {/ Root /}
<view> {/ Track Positioner /}
<view style={{ left: `${ratio * 100}%` }} /
/view>
/view>
);
{/
Thumb
}
/}
30. Main
<Slider />
31. Main
Background
<Slider />
32. Main
Background
Paint
<Slider />
33. Main
Paint
CreateElement,'view',2,
OperationTagId
InsertBefore,
Operation
Background
<Slider />
1,2,
3,
ParentChild Before
34. Main
Background
Idle
<Slider />
Paint
35. Main
Background
JS
Paint
<Slider />
36. Main
Background
<Slider />
Paint
<Slider />
37. main-thread.js (IFR)
background.js
export function App() {
const [alterLogo, setAlterLogo] = useState(false);
export function App() {
const [alterLogo, setAlterLogo] = useState(false);
useEffect(()
{
console.info('Hello, world');
}, []);
const onTap = useCallback(()
setAlterLogo((prevAlterLogo)
}, []);
Eliminating Side Effect Code
{
!prevAlterLogo);
return (
<view bindtap={onTap}>
<image src={alterLogo ? reactLynxLogo : lynxLogo} /
/view>
);
}
}
return (
<view>
<image src={alterLogo ? reactLynxLogo : lynxLogo} /
/view>
);
38. FCP
Main
Background
<Slider />
Paint
<Slider />
39. Instant First-Frame Rendering
帧直出
Display instantly when the page loads
FCP
Main
IFR
Paint
40. FCP
Main
Background
IFR
Paint
<Slider />
41. FCP
Main
Background
IFR
Paint
<Slider />
Hydration
42. function Slider({ min, max, initialValue, onChange }) {
const [value, setValue] = useState(initialValue);
const ratio = valueToRatio(value, min, max);
return (
<view> {/ Root /}
<view> {/ Track Positioner /}
<view style={{ left: `${ratio * 100}%` }} /
/view>
/view>
);
{/
Thumb
}
/}
43. function Slider({ min, max, initialValue, onChange }) {
const [value, setValue] = useState(initialValue);
const ratio = valueToRatio(value, min, max);
return (
<view bindtouchmove={handlePointerMove}> {/ Root /}
<view> {/ Track Positioner /}
<view style={{ left: `${ratio * 100}%` }} /
{/ Thumb
/view>
/view>
);
}
/}
44. function Slider({ min, max, initialValue, onChange }) {
const [value, setValue] = useState(initialValue);
const ratio = valueToRatio(value, min, max);
const handlePointerMove = (e)
{
const nextValue = calcValue(e.detail.x, trackPosRef);
setValue(nextValue);
onChange (nextValue);
};
return (
<view bindtouchmove={handlePointerMove}> {/ Root /}
<view> {/ Track Positioner /}
<view style={{ left: `${ratio * 100}%` }} /
{/ Thumb
/view>
/view>
);
}
/}
45. Main
Background
handlePointerMove
46. Main
Background
touchmove
handlePointerMove
47. Main
Background
touchmove
handlePointerMove
48. Main
Background
touchmove
Paint
handlePointerMove
49. Frame
Main
Background
touchmove
Delay by one frame
Paint
handlePointerMove
50. Frame
Main
Background
touchmove
Long Task
handlePointerMove
51.
52. Frame
Main
touchmove
“Cross-Thread Latency”
Background
Long Task
handlePointerMove
53. Frame
Main
Background
touchmove
handlePointerMove
Long Task
Paint
54. const handlePointerMove = (e)
{
const nextValue = calcValue(e.detail.x, trackPosRef);
setValue(nextValue);
onChange (nextValue);
};
return (
<view bindtouchmove={handlePointerMove}>
<view bindlayoutchange={handleTrackLayoutChange}>
<view style={{ left: `${ratio * 100}%` }} /
/view>
/view>
);
55. const handlePointerMove = (e)
{
const nextValue = calcValue(e.detail.x, trackPosRef);
setValue(nextValue);
onChange (nextValue);
};
return (
<view main-thread:bindtouchmove={handlePointerMove}>
<view bindlayoutchange={handleTrackLayoutChange}>
<view style={{ left: `${ratio * 100}%` }} /
/view>
/view>
);
56. const handlePointerMove = (e)
{
'main thread';
const nextValue = calcValue(e.detail.x, trackPosRef);
setValue(nextValue);
onChange (nextValue);
};
return (
<view main-thread:bindtouchmove={handlePointerMove}>
<view bindlayoutchange={handleTrackLayoutChange}>
<view style={{ left: `${ratio * 100}%` }} /
/view>
/view>
);
57. Main
touchmove
handlePointerMove
Paint
58. Main Thread Function
主线程函数
General programmability on the main thread
Main
touchmove
handlePointerMove
Paint
59. background.js
const handlePointerMove = (e)
{
'main thread';
const nextValue = calcValue(e.detail.x, trackPosRef);
setValue(nextValue);
onChange (nextValue);
};
<view main-thread:bindtouchmove={handlePointerMove}>
main-thread.js
60. background.js
<view main-thread:bindtouchmove={handlePointerMove}>
main-thread.js
const handlePointerMove = (e)
{
'main thread';
const nextValue = calcValue(e.detail.x, trackPosRef);
setValue(nextValue);
onChange (nextValue);
};
61. background.js
<view main-thread:bindtouchmove={handlePointerMove}>
main-thread.js
const handlePointerMove = (e)
{
'main thread';
const nextValue = calcValue(e.detail.x, trackPosRef);
setValue(nextValue);
onChange (nextValue);
};
62. background.js
const handlePointerMove = {
mainThreadFunctionId: 1
}
<view main-thread:bindtouchmove={handlePointerMove}>
main-thread.js
const handlePointerMove = (e)
{
'main thread';
const nextValue = calcValue(e.detail.x, trackPosRef);
setValue(nextValue);
onChange (nextValue);
};
63. background.js
const handlePointerMove = {
mainThreadFunctionId: 1
}
<view main-thread:bindtouchmove={handlePointerMove}>
main-thread.js
const handlePointerMove = (e)
{
'main thread';
const nextValue = calcValue(e.detail.x, trackPosRef);
setValue(nextValue);
onChange (nextValue);
};
const mainThreadFunctionMap = {
1: handlePointerMove
}
64. const handlePointerMove = (e)
{
'main thread';
const nextValue = calcValue(e.detail.x, trackPosRef);
setValue(nextValue); ⚠
onChange (nextValue);
};
return (
<view main-thread:bindtouchmove={handlePointerMove}>
<view bindlayoutchange={handleTrackLayoutChange}>
<view style={{ left: `${ratio * 100}%` }} /
/view>
/view>
);
65. const handlePointerMove = (e)
{
'main thread';
const nextValue = calcValue(e.detail.x, trackPosRef);
writeValue(nextValue); ✅
onChange (nextValue);
};
return (
<view main-thread:bindtouchmove={handlePointerMove}>
<view bindlayoutchange={handleTrackLayoutChange}>
<view style={{ left: `${ratio * 100}%` }} /
/view>
/view>
);
66. const handlePointerMove = (e)
{
'main thread';
const nextValue = calcValue(e.detail.x, trackPosRef);
writeValue(nextValue);
onChange (nextValue);
};
67. const ratioRef = useMainThreadRef(valueToRatio(initialValue, min, max));
const writeValue = (nextValue)
{
'main thread';
ratioRef.current = mtsValueToRatio(nextValue, min, max);
updateThumbStyle();
};
const handlePointerMove = (e)
{
'main thread';
const nextValue = calcValue(e.detail.x, trackPosRef);
writeValue(nextValue);
onChange (nextValue);
};
68. const ratioRef = useMainThreadRef(valueToRatio(initialValue, min, max));
const updateThumbStyle = ()
{
'main thread';
thumbRef.current setStyleProperties({
left: `${ratioRef.current * 100}%`,
});
};
69. const thumbRef = useMainThreadRef(null);
const ratioRef = useMainThreadRef(valueToRatio(initialValue, min, max));
const updateThumbStyle = ()
{
'main thread';
thumbRef.current setStyleProperties({
left: `${ratioRef.current * 100}%`,
});
};
return (
<view main-thread:bindtouchmove={handlePointerMove}>
<view main-thread:bindlayoutchange={handleTrackLayoutChange}>
<view main-thread:ref={thumbRef} /
/view>
/view>
);
70. function Slider({ min, max, initialValue, onChange }) {
const trackPosRef = useMainThreadRef(null);
const handleTrackLayoutChange = useTrack(trackPosRef);
const thumbRef = useMainThreadRef(null);
const ratioRef = useMainThreadRef(valueToRatio(initialValue, min, max));
const updateThumbStyle = ()
{
'main thread';
thumbRef.current setStyleProperties({
left: `${ratioRef.current * 100}%`,
});
};
const writeValue = (nextValue)
{
'main thread';
ratioRef.current = mtsValueToRatio(nextValue, min, max);
updateThumbStyle();
};
const handlePointerMove = (e)
{
'main thread';
const nextValue = calcValue(e.detail.x, trackPosRef);
writeValue(nextValue);
onChange (nextValue);
};
const initThumb = (ref)
'main thread';
thumbRef.current = ref;
updateThumbStyle();
};
{
return (
<view main-thread:bindtouchmove={handlePointerMove}>
<view main-thread:bindlayoutchange={handleTrackLayoutChange}>
<view main-thread:ref={initThumb} /
/view>
/view>
);
}
71. Main Thread Function
Execute on the Main Thread
const handlePointerMove = (e)
'main thread’;
};
{
Direct Element Manipulation
thumbRef.current setStyleProperties({
left: `${ratioRef.current * 100}%`,
});
<view main-thread:ref={thumbRef}>
<view main-thread:bindtouchmove={handlePointerMove}>result = await runOnMainThread(mtFunction)(args);
result = await runOnBackground(bgFunction)(args);
Cross Thread Communication
Main Thread Event
72. Can we do better?
73. function Slider({ min, max, initialValue, onChange }) {
const trackPosRef = useRef(null);
const handleTrackLayoutChange = useTrack(trackPosRef);
const [value, setValue] = useState(initialValue);
const ratio = valueToRatio(value, min, max);
const handlePointerMove = (e)
{
const nextValue = calcValue(e.detail.x, trackPosRef);
setValue(nextValue);
onChange (nextValue);
};
return (
<view bindtouchmove={handlePointerMove}>
<view bindlayoutchange={handleTrackLayoutChange}>
<view style={{ left: `${ratio * 100}%` }} /
/view>
/view>
);
}
74. function Slider({ min, max, initialValue, onChange }) {
const trackPosRef = useMainThreadRef(null);
const handleTrackLayoutChange = useTrack(trackPosRef);
const thumbRef = useMainThreadRef(null);
function Slider({ min, max, initialValue, onChange }) {
const trackPosRef = useRef(null);
const handleTrackLayoutChange = useTrack(trackPosRef);
const ratioRef = useMainThreadRef(valueToRatio(initialValue, min, max));
const updateThumbStyle = ()
{
'main thread';
thumbRef.current setStyleProperties({
left: `${ratioRef.current * 100}%`,
});
};
const [value, setValue] = useState(initialValue);
const ratio = valueToRatio(value, min, max);
const writeValue = (nextValue)
{
'main thread';
ratioRef.current = mtsValueToRatio(nextValue, min, max);
updateThumbStyle();
};
const handlePointerMove = (e)
{
const nextValue = calcValue(e.detail.x, trackPosRef);
setValue(nextValue);
onChange (nextValue);
};
const handlePointerMove = (e)
{
'main thread';
const nextValue = calcValue(e.detail.x, trackPosRef);
writeValue(nextValue);
onChange (nextValue);
};
return (
<view bindtouchmove={handlePointerMove}>
<view bindlayoutchange={handleTrackLayoutChange}>
<view style={{ left: `${ratio * 100}%` }} /
/view>
/view>
);
const initThumb = (ref)
'main thread';
thumbRef.current = ref;
updateThumbStyle();
};
return (
<view main-thread:bindtouchmove={handlePointerMove}>
<view main-thread:bindlayoutchange={handleTrackLayoutChange}>
<view main-thread:ref={initThumb} /
/view>
/view>
);
}
}
{
75. Main
Background
Paint
<Slider />
76. Main
Background
<Slider />
Paint
77. function Slider({ min, max, initialValue, onChange }) {
const trackPosRef = useRef(null);
const handleTrackLayoutChange = useTrack(trackPosRef);
const [value, setValue] = useState(initialValue);
const ratio = valueToRatio(value, min, max);
const handlePointerMove = (e)
{
const nextValue = calcValue(e.detail.x, trackPosRef);
setValue(nextValue);
onChange (nextValue);
};
return (
<view bindtouchmove={handlePointerMove}>
<view bindlayoutchange={handleTrackLayoutChange}>
<view style={{ left: `${ratio * 100}%` }} /
/view>
/view>
);
}
78. 'main thread';
function Slider({ min, max, initialValue, onChange }) {
const trackPosRef = useRef(null);
const handleTrackLayoutChange = useTrack(trackPosRef);
const [value, setValue] = useState(initialValue);
const ratio = valueToRatio(value, min, max);
const handlePointerMove = (e)
{
const nextValue = calcValue(e.detail.x, trackPosRef);
setValue(nextValue);
onChange (nextValue);
};
79. Main
<Slider />
Paint
80. Main Thread Component
主线程组件
Component abstraction on the main thread
Main
<Slider />
Paint
81. Dugyu/mtc-color-picker
82. function HueSlider({
initialSL = [100, 50],
['main-thread:writeSL']: writeSL,
restProps
}: HueSliderProps) {
const [gradients] = useState(()
{
return HSLGradients.hueGradientPair(initialSL[0], initialSL[1]);
});
const currentSLRef = useMainThreadRef<Vec2>(initialSL);
const writeRootStyle = useMainThreadRef<Writer<Record<string, string > ();
const writeTrackStyle = useMainThreadRef<Writer<Record<string, string > ();
function ColorPicker({ initialValue, onChange}) {
const hueRef = useMainThreadRef(initialValue[0]);
const writeSL = useMainThreadRef();
const satRef = useMainThreadRef(initialValue[1]);
const writeHL = useMainThreadRef();
const lightRef = useMainThreadRef(initialValue[2]);
const writeHS = useMainThreadRef();
const updateStyle = (next: WriteAction<Vec2>)
{
'main thread';
const resolved = resolveNextValue(currentSLRef.current, next);
if (resolved
undefined) {
const { edge: edgeBg, track: trackBg } = MTSHSLGradients.hueGradientPair(
resolved[0],
resolved[1],
);
writeRootStyle.current ({ 'background-image': edgeBg });
writeTrackStyle.current ({ 'background-image': trackBg });
}
};
const init = useCallback(()
{
'main thread';
if (writeSL) {
writeSL.current = updateStyle;
}
}, []);
const writeSliderGradients = ()
{
'main thread';
writeSL current ([satRef.current, lightRef.current]);
writeHL current ([hueRef.current, lightRef.current]);
writeHS current ([hueRef.current, satRef.current]);
};
const forwardOnHSLChange = ()
{
'main thread';
writeSliderGradients();
onChange ([hueRef.current, satRef.current, lightRef.current]);
};
return (
<view>
<HueSlider
initialValue={initialValue[0]}
main-thread:onChange={()
{
'main thread';
hueRef.current = h;
forwardOnHSLChange();
}}
initialSL={[initialValue[1], initialValue[2]]}
main-thread:writeSL={writeSL}
/
{/
/}
/view>
);
return (
<Slider
min={0}
max={360}
step={1}
main-thread:onInit={init}
main-thread:writeRootStyle={writeRootStyle}
main-thread:writeTrackStyle={writeTrackStyle}
initialRootStyle={{ 'background-image': gradients.edge }}
initialTrackStyle={{ 'background-image': gradients.track }}
{
restProps}
/
);
}
}
83. 'main thread';
'main thread';
function ColorPicker({ initialValue, onChange }) {
const [h, setH] = useState(initialValue[0]);
const [s, setS] = useState(initialValue[1]);
const [l, setL] = useState(initialValue[2]);
return (
<view>
<HueSlider
s={s}
l={l}
initialValue={initialValue[0]}
onChange={(hue)
{
setH(hue);
onChange ([hue, s, l]);
}}
/
{/
/}
/view>
);
}
function HueSlider({
s = defaultSaturation,
l = defaultLightness,
restProps
}: HueSliderProps) {
const gradients = HSLGradients.hueGradientPair(s, l);
return (
<Slider
min={0}
max={360}
step={1}
rootStyle={{ backgroundImage: gradients.edge }}
trackStyle={{ backgroundImage: gradients.track }}
{
restProps}
/
);
}
84. Main Thread Component
85. Main Thread Component
Component on the Main Thread
'main thread';
function Slider(initialValue) {
const [value, setValue] = useState(initialValue);
};
86. Main Thread Component
Component on the Main Thread
'main thread';
function Slider(initialValue) {
const [value, setValue] = useState(initialValue);
};
Flexible Composition
return (
<BTC>
<MTC>
<BTC2 /
/MTC>
/BTC>
);
87. Main Thread Component
Component on the Main Thread
Imperative Escape Hatch
'main thread';
function Slider(initialValue) {
const [value, setValue] = useState(initialValue);
};
Flexible Composition
return (
<BTC>
<MTC>
<BTC2 /
/MTC>
/BTC>
);
thumbRef.current setStyleProperties({
left: `${ratio * 100}%`,
});
88. Main Thread Component
Component on the Main Thread
Imperative Escape Hatch
'main thread';
function Slider(initialValue) {
const [value, setValue] = useState(initialValue);
};
Flexible Composition
return (
<BTC>
<MTC>
<BTC2 /
/MTC>
/BTC>
);
thumbRef.current setStyleProperties({
left: `${ratio * 100}%`,
});
Background Function
const handleChange = (v)
'background';
setValue(v);
};
{
<Slider onChange={handleChange} / ;
89. 双线程的 React:
ReactLynx
90. Haoyang Wang (王浩阳) / @pupiltong
91. const App = ()
(
<view className='App'>
<LottieGrid
size={GRID_SIZE}
render={({ i })
<HEICImage src={getImageUrls(i)} /
/
<Button bindtap={handleRestart}>
RESTART
/Button>
/view>
);
};
92. const App = ()
(
<view className='App'>
<LottieGrid
size={GRID_SIZE}
render={({ i })
<HEICImage src={getImageUrls(i)} /
/
<Button bindtap={handleRestart}>
RESTART
/Button>
/view>
);
};
93. @keyframes lottie-border-light {
0% {
border-color: transparent;
}
25% {
border-color: #c96ed1;
}
}
94. const App = ()
(
<view className='App'>
<LottieGrid
size={GRID_SIZE}
render={({ i })
<HEICImage src={getImageUrls(i)} /
/
<Button bindtap={handleRestart}>
RESTART
/Button>
/view>
);
};
95. const App = ()
(
<view className='App'>
<LottieGrid
size={GRID_SIZE}
render={({ i })
<HEICImage src={getImageUrls(i)} /
/
<Button bindtap={handleRestart}>
RESTART
/Button>
/view>
);
};
96. const HEICImage = ({ src })
{
const [imageSrc, setImageSrc] = useState(null);
useEffect(()
{
const decodedImage = await decodeHeicImage(src);
setImageSrc(decodedImage);
}, [src]);
return (
imageSrc
? <ImageRender className={'image'} src={imageSrc} /
: <Skeleton /
);
};
97. const HEICImage = ({ src })
{
const [imageSrc, setImageSrc] = useState(null);
useEffect(()
{
const decodedImage = await decodeHeicImage(src);
setImageSrc(decodedImage);
}, [src]);
LONG TASK!!!
return (
imageSrc
? <ImageRender className={'image'} src={imageSrc} /
: <Skeleton /
);
};
98. Frame
Main
decodeHeicImage
99. Frame
Main
decodeHeicImage
Main
Paint
Lost frames
100. Main
Background
Paint
decodeHeicImage
Paint
Paint
Paint
101. Main
Background
Paint
<HEICImage /
Paint
<HEICImage /
Paint
Paint
102. Background
<HEICImage /
103. Try it yourself
Background
<HEICImage /
104. Background React for Web
Web 上的后台 React
React rendered in the Web Worker by default
Background
<HEICImage />
Apply
105. 如何实现?
106. ReactLynx Code
ReactLynx Framework
Lynx Engine
iOS UI Kit view
Android Platform view
107. JavaScript
ReactLynx Code
BundleReactLynx Framework
LynxLynx Engine
Engine
iOS UI Kit view
Android Platform view
108. JavaScript
ReactLynx Code
BundleReactLynx Framework
LynxLynx Engine
Engine
iOS UI Kit view
Android Platform view
109. Lynx
JavaScript
WEB
ReactLynx Code
?
BundleReactLynx Framework
LynxLynx Engine
Engine
iOS
Android
110. Lynx
JavaScript
WEB
ReactLynx Code
BundleReactLynx Framework
LynxLynx Engine
Engine
iOS
Android
React.js ?
111. Lynx
mainthread.js
JavaScript
WEB
background.js
ReactLynx CodeReactLynx Code
BundleReactLynx Framework
LynxLynx Engine
Engine
iOS
Android
React.js?
112. Lynx
mainthread.js
WEB
background.js
ReactLynx Code
JavaScript
IFR
Bundle
Hooks
ReactLynx Framework
Lynx Engine
Lynx
Engine
MTS
iOS
Android
React.js?
113. LynxWEB
mainthread.jsbackground.js
ReactLynx Code
JavaScript
IFR
Bundle
Hooks
ReactLynx Framework
Lynx Engine
Lynx
Engine
MTS
iOS
Android
React.js?
Hooks
114. Lynx
ReactLynx Code
JavaScript
Bundle
ReactLynx Framework
Lynx Engine
Lynx
Engine
WEB
iOS
Android
115. Lynx
WEB
ReactLynx Code
CSS
Artifact
ReactLynx Framework
Lynx Engine
Lynx
Engine
iOS
Android
116. Lynx
WEB
ReactLynx Code
CSS
Artifact
ReactLynx Framework
Lynx Engine
Lynx
Engine
iOS
Android
117. Lynx
WEB
ReactLynx Code
CSS
Artifact
ReactLynx Framework
Lynx Engine
Lynx
Engine
?
iOS
Android
118. Lynx
WEB
ReactLynx Code
CSS
Artifact
ReactLynx Framework
Lynx Engine
Lynx
Engine
iOS
Styling Engine
Android
Paint Engine
119. Styling Engine
Paint Engine
120. Styling Engine
<view>
<view>
<image>
Paint Engine
121. Styling Engine
Paint Engine
.lottie-grid {
display:grid;
}
<view>
<view>
<image>
+
.lottie-grid image {
height:100%;
width:100%;
aspect-ratio: 1;
}
=
122. Styling Engine
Paint Engine
.lottie-grid {
display:grid;
}
<view>
<view>
<image>
+
.lottie-grid image {
height:100%;
width:100%;
aspect-ratio: 1;
}
=
123. Styling Engine
起测试
124. Styling Engine
Paint Engine
125. Styling EnginePaint Engine
WASMWASM
126. Styling EnginePaint Engine
WASMWASM
WASMBrowser
127. Styling EnginePaint Engine
WASMWASM
WASMBrowser
BrowserBrowser
128. Styling EnginePaint Engine
WASMWASM
WASMBrowser
BrowserBrowser
BrowserWASM
129. <view>
<view>
WASM Engine
canvas
<image>
WASM Styling Engine
+
WASM Paint Engine
130. canvas
WASM Styling Engine
+
WASM Paint Engine
131. HTML
<body>
Lost the original tree structure
HTML
content
Accessibility
Testing
canvas
WASM Styling Engine
+
WASM Paint Engine
132. HTMLEle
<view>
HTMLEle
<view>
Paint
WASM Engine
HTMLEle
<image>
position:absolute
WASM Styling Engine
+
HTMLElement
133. FCP
ReactLynx
IFR
WASM Styling Engine
+
HTMLElement
134. FCP
ReactLynx
IFR
WASM loading
WASM Styling Engine
+
HTMLElement
135. FCP
ReactLynx
IFR
WASM loading
太慢了
WASM Styling Engine
+
HTMLElement
136. <view>
Paint
HTMLEle
<view>
HTMLElement
HTMLEle
<view>
HTMLEle
Browser Styling Engine
+
HTMLElement
137. .lottie-grid image {
height:100%;
width:100%;
aspect-ratio: 1;
}
<image>
HTMLEle
?
138. .lottie-grid image {
height:100%;
width:100%;
aspect-ratio: 1;
}
<image>
HTMLEle
tag=“image”
139. .lottie-grid image {
height:100%;
width:100%;
aspect-ratio: 1;
}
.lottie-grid [l-tag=“image”]{
height:100%;
width:100%;
aspect-ratio: 1;
}
140. .lottie-grid {
display:grid;
}
.lottie-grid image {
height:100%;
width:100%;
aspect-ratio: 1;
}
141. Web
Lynx
142. Grid, aspect-ratio…
Web
Lynx
143. Grid, aspect-ratio…
Web
Lynx
<image>HTMLEle
display:grid;display:grid;
144. Web
<view>
display:linear;
<view>
Lynx
Linear…
<view>
145. Web
<view>
Lynx
Linear…
display:linear;
HTML
Ele
display:flex;
<view>HTML
Eleflex:none;
<view>HTML
Eleflex:none;
146. Web
<view>
display:linear;
HTML
Ele
<view>
Lynx
Linear…
<view>
Rust
transformer
display:flex;
HTML
Eleflex:none;
HTML
Eleflex:none;
147. -40% IFR time
JavaScript Transformer
Rust WASM Transformer
148. Web
Lynx
149. Lynx
WEB
ReactLynx Code
CSS
Artifact
ReactLynx Framework
Lynx Engine
Lynx
Engine
iOS
Styling Engine
Android
Paint Engine
150. Lynx Engine
Lynx
Engine
iOS
Styling Engine
Android
Paint Engine
151. <view>
<image>
<text>
152. <div>
<view>
<image><img>
<text><div>
<p>
153. <div>
<view>
.text {
background: green;
}
<img>
<image>
<div>
<text>
<p>
154. <div>
<view>
.text > .text {
background: green;
}
<image><img>
<text><div>
<text>
<p>?
<div>?
155. <x-view>
<view>
.text > .text {
background: green;
}
<x-image>
<image>
Shadow
<x-text>
<text>
Tree
<p>
<text>
<x-text>
156. JavaScript
ReactLynx Code
BundleReactLynx Framework
LynxBrowser Styling Engine
EngineWeb Components
157. Lynx Web Platform
Lynx 的 Web 平台
Lynx Engine on the Web Browser
Browser Styling Engine
Web Components
持
158.
159. 现已公开测试:
Lynx for Web
160.
161. ReactLynx
162. ReactLynx
Lynx for Web
163. 并
性能
JavaScriptSync
BackgroundJavaScriptAsync
Main
164. 编程结构
MainReactSync
BackgroundReactAsync
165. 未来前端?
GUI
React
Lynx
Web
AI
166. Mobile
Software
x86 ⏩ ARM
167. MobileAI
SoftwareSoftware
x86 ⏩ ARMCPU ⏩ GPU
168. 古法
新 ⋅ ⋅前端
前端
169. 🫵
新 ⋅ 前端
古法 ⋅ 前端
170. 新 ⋅ 前端
古法 ⋅ 前端