surmon.me.native代码分析笔记
surmon.me.native是一个适合入门学习的react-native博客内容展示项目,代码组织优良值得借鉴。
基础样式
作者把基础样式进行了统一编写,方便维护修改。
style/size.js
import { Dimensions, Platform } from 'react-native';
const { width, height } = Dimensions.get('window');
const screenHeight = width < height ? height : width;
const screenWidth = width < height ? width : height;
export default {
// Window Dimensions
screen: {
height: screenHeight,
width: screenWidth,
widthHalf: screenWidth * 0.5,
widthThird: screenWidth * 0.333,
widthTwoThirds: screenWidth * 0.666,
widthQuarter: screenWidth * 0.25,
widthThreeQuarters: screenWidth * 0.75,
},
// Navbar
navbarHeight: (Platform.OS === 'ios') ? 50 : 50,
statusBarHeight: (Platform.OS === 'ios') ? 16 : 24,
// Padding
padding: 20
};
style/fonts.js
import { Platform } from 'react-native';
function lineHeight(fontSize) {
const multiplier = (fontSize > 20) ? 0.1 : 0.33;
return parseInt(fontSize + (fontSize * multiplier), 10);
}
const base = {
fontSize: 14,
lineHeight: lineHeight(14),
...Platform.select({
ios: {
// fontFamily: 'HelveticaNeue',
},
android: {
fontFamily: 'Roboto',
},
}),
};
export default {
base: { ...base },
h1: { ...base, fontSize: base.fontSize * 1.75, lineHeight: lineHeight(base.fontSize * 2) },
h2: { ...base, fontSize: base.fontSize * 1.5, lineHeight: lineHeight(base.fontSize * 1.75) },
h3: { ...base, fontSize: base.fontSize * 1.25, lineHeight: lineHeight(base.fontSize * 1.5) },
h4: { ...base, fontSize: base.fontSize * 1.1, lineHeight: lineHeight(base.fontSize * 1.25) },
h5: { ...base },
};
欢迎页 welcome.js
编写欢迎页面提高用户体验,据说可以防止启动白屏。
// Init Layout
import Layout from './layout.js';
// Styles
import { AppColors, AppSizes } from '@app/style';
const styles = StyleSheet.create({
container: {
flex: 1,
backgroundColor: AppColors.background,
alignItems: 'center',
justifyContent: 'center'
},
launchImage: {
position: 'absolute',
left: 0,
top: 0,
width: AppSizes.screen.width,
height: AppSizes.screen.height
}
});
class Welcome extends Component {
componentWillMount () {
var navigator = this.props.navigator;
setTimeout (() => {
navigator.replace({component: Layout, passProps: { navigator }});
}, 1666);
}
render () {
return (
<View style={styles.container}>
<StatusBar
translucent={true}
backgroundColor={'#rgba(0, 0, 0, 0)'}
barStyle="light-content"
showHideTransition='slide'
hidden={false}
/>
<Image style={styles.launchImage} source={require('@app/images/android-launch/launch-image.png')}></Image>
</View>
);
}
}
export default Welcome;
菜单页 menu.js
作者实现了安卓版本的屏幕左划出效果,编写子组件MneuHeader(菜单头部),MenuList(菜单列表)、MenuItem(菜单列表项)组合成Menu组件。
class Menu extends Component {
constructor(props) {
super(props);
this.state = {
selectedItem: props.initialEntry || props.entries[0].id//默认指向第一个列表
}
}
//点击菜单任意列表时,关闭菜单
_onSectionChange = (section) => {
this.setState({selectedItem: section});
this._drawer.closeDrawer();
}
//打开菜单
_openMenu = () => {
this._drawer.openDrawer();
}
//渲染菜单
_renderNavigationView = () => {
return (
<View style={
this.props.containerStyle}>
<MneuHeader userInfo={
this.props.userInfo}/>
<MenuList
items={
this.props.entries}
selectedItem={
this.state.selectedItem}
tintColor={
this.props.tintColor}
onSectionChange={
this._onSectionChange}
/>
</View>
)
}
//渲染菜单内容
_renderContent() {
const element = this.props.entries.find(entry => entry.id === this.state.selectedItem).element;
if (element) {
return React.cloneElement(element, {openMenu: this._openMenu});
}
}
//使用DrawerLayoutAndroid组件,渲染菜单
render() {
return (
<DrawerLayoutAndroid
ref={(ref) => {
this._drawer = ref}}
{...this.props}
renderNavigationView={
this._renderNavigationView}>
{
this._renderContent()}
</DrawerLayoutAndroid>
)
}
}
export default Menu;
API
作者将网络请求进行封装,增加了API的复用性。
import showToast from '&#