在 Android 开发中,从传统的 XML + ConstraintLayout 到 Jetpack Compose 的 Modifier,布局系统经历了一次大进化。而在 React Native 中,整个世界的布局核心只有一个:Flexbox。
1. 样式对象 vs Modifier
在 Compose 中,我们通过链式调用 Modifier 来修饰 UI 组件。 在 RN 中,样式是通过 JavaScript 对象(通常用 StyleSheet.create)传递给组件的 style 属性的。
Compose 示例
scss
// Compose
Box(
modifier = Modifier
.fillMaxWidth()
.padding(16.dp)
.background(Color.Red)
) {
Text("Hello Android")
}
React Native 示例
javascript
// React Native
import { View, Text, StyleSheet } from 'react-native';
export default function App() {
return (
<View style={styles.container}>
<Text>Hello React Native</Text>
</View>
);
}
const styles = StyleSheet.create({
container: {
width: '100%', // Modifier.fillMaxWidth()
padding: 16, // Modifier.padding(16.dp)
backgroundColor: 'red', // Modifier.background(Color.Red)
},
});
注意:RN 中的尺寸(如 16)默认是以设备独立像素(dp)为单位的,不需要显式写 .dp。
2. Flexbox 布局 vs Row/Column/Box
Compose 提供了 Row、Column 和 Box 作为基础布局容器。 RN 默认所有 <View> 都是 Flex 容器,它的布局方向默认为纵向(即类似 Column)。
| Compose 布局 | RN Flexbox 属性 | 说明 |
|---|---|---|
Column |
flexDirection: 'column' |
RN 默认值,子元素纵向排列 |
Row |
flexDirection: 'row' |
子元素横向排列 |
Box (叠加) |
position: 'absolute' |
绝对定位,脱离文档流 |
排列与对齐 (Arrangement & Alignment)
在 Compose 中,我们使用 horizontalArrangement 和 verticalAlignment(对于 Row)。 在 RN 中,主轴的排列由 justifyContent 决定,交叉轴的对齐由 alignItems 决定。
arduino
// 等价于 Compose 的 Row(horizontalArrangement = Arrangement.SpaceBetween, verticalAlignment = Alignment.CenterVertically)
const rowStyle = {
flexDirection: 'row',
justifyContent: 'space-between', // 主轴 (横向) 排布
alignItems: 'center', // 交叉轴 (纵向) 对齐
};
3. Weight 权重 vs flex 属性
在 Compose 中,我们使用 Modifier.weight(1f) 来让组件占据剩余空间。 在 RN 中,对应的是 flex: 1。
ini
<View style={{ flexDirection: 'row' }}>
<View style={{ flex: 1, backgroundColor: 'blue' }} /> // 占据 1/3
<View style={{ flex: 2, backgroundColor: 'green' }} /> // 占据 2/3
</View>
4. ConstraintLayout 呢?
React Native 并没有官方的 ConstraintLayout。绝大多数复杂的布局都可以通过多层嵌套的 Flexbox (View) 或者绝对定位 (position: 'absolute') 来实现。虽然嵌套在 Android 传统 XML 时代是性能杀手,但在 React Native 的 Flexbox 引擎(Yoga)优化下,合理的嵌套并不会带来明显的性能损耗。
核心总结
从 Android 转 RN,你需要抛弃 ConstraintLayout 的思维,全面拥抱一维布局体系(主轴与交叉轴)。将 Row 和 Column 的思维映射到 flexDirection,用 justifyContent 和 alignItems 处理对齐,你会发现 Flexbox 其实非常强大且直观。