React Native 项目2(One 【一个】客户端)

前段时间开始学习React Native,然后试着开始做一个小项目,在练手的同时,分享出来希望和各位同学互相学习react-native项目。之前写过项目相关的文章,没看过的同学可以参考一下:

React Native项目效果

目前项目完成了(One 【一个】)主体界面功能,当然功能和原App还有较大的差距,之前主要对ios进行了适配,这两天对Android也进行了一些调整。有什么bug大家可以评论或者在github上提issue。先看一下效果图:

Paste_Image.png
Paste_Image.png
Paste_Image.png
Paste_Image.png
Paste_Image.png

这里贴的是ios的效果图,android端的类似。接下来介绍项目的结构,用到的一些第三方库,以及项目过程中的小坑。

项目结构

  • Pages
    项目的主要界面,目录下有One、Douban、Zhihu三个文件夹,分别对应one、豆瓣、知乎日报三个应用,其中one是完成度相对比较高的,其他两个应用界面很少。
  • Assets
    目录下存放了项目中用到了一些图标,这里存放的是android和ios的共有图标,比如one主界面下面的四个图标。android和ios的launch icon是在各自工程中分别设置的。
  • Constants
    定义项目中的常量
  • Components
    项目的一些自定义components,可以在多个pages中使用。
  • Styles
    定义常用的界面style,使用时可以直接引用,模拟android的styles,这样就不需要在每个page中重复定义styles
  • Utils
    定义常用的一些工具类,如网络请求、时间格式、展示属性等。
  • Actions
  • reducers
  • sagas
    这三个目录是redux相关的一些方法,相关的介绍可以查看 React native 项目进阶(redux, redux saga, redux logger),当然阅读之前最好有redux基础,推荐redux的学习教程:
    http://leonshi.com/redux-saga-in-chinese/index.html
    http://cn.redux.js.org/index.html

第三方库

React Native 从第一次提交到现在已经有20个月的时间,目前github上有近4万star,很多大牛贡献了各种第三方库,目前开始学习React Native对于新人初学者来说文档和社区非常友好。这里罗列下用到的第三方库:

    "react-native-button": "github:ide/react-native-button",
    "react-native-datepicker": "^1.3.2",
    "react-native-drawer": "^2.2.2",
    "react-native-fs": "^2.0.1-rc.2",
    "react-native-root-toast": "^1.0.3",
    "react-native-router-flux": "[3.30.1]",
    "react-native-scrollable-tab-view": "0.6.0",
    "react-native-sound": "^0.8.3",
    "react-native-viewpager": "^0.2.1",
    "react-redux": "^4.4.5",
    "redux": "^3.6.0",
    "redux-logger": "^2.6.1",
    "redux-saga": "^0.11.1"

其中部分比较简单,有些在之前的文章中进行了介绍,下面主要介绍:

    "react-native-viewpager": "^0.2.1",
    "react-native-scrollable-tab-view": "0.6.0",
    "react-native-sound": "^0.8.3",
    "react-native-fs": "^2.0.1-rc.2",  

React-Native-ViewPager

是一个viewpager,one项目中的首页、文章页、音乐页均使用了viewpager,使用率很高,先看一个demo:

                   <ViewPager
                        dataSource={this.state.banners}
                        renderPage={this.renderBanners}
                        isLoop={true}
                        autoPlay={true}
                    />

dataSource定义数据源,其数据源的定义过程是:

        var bannerDataSource = new ViewPager.DataSource({
            pageHasChanged: (p1, p2) => p1 !== p2,
        });  

        banners: bannerDataSource.cloneWithPages([]),

renderPage用于展示每个pager的界面

    renderBanners(data, pageID) {
        return (
            <Image style={{
                height: 140,
                width: deviceWidth,
            }} source={{uri: data.cover}}>
            </Image>
        );
    }

isLoop 是否轮播

autoPlay 是否自动播放

renderPageIndicator定义indicator的样式 ,当然可以使用default的样式,这里是一个示例,隐藏掉indicator:

renderPageIndicator={()=>(<View style={{width: 0, height: 0}}></View>)}

react-native-scrollable-tab-view

react-native-scrollable-tab-view用于定义应用的主tab,项目中主要定义了one的四个tab,可以滑屏幕切换界面,在项目中由于各个子界面自身有左右切换的需求,因此关闭了该功能。

部分设置

**renderTabBar
**
自定义tabbar,如项目中自定义了四个tab的样式

**onChangeTab
**
当tab切换时回调

**locked
**
是否锁定,锁定时不能左右滑动

**page
**
设置选中的tab

项目使用示例:

           <ScrollableTabView initialPage={0} locked={true} prerenderingSiblingsNumber={1} tabBarPosition="bottom"
                               renderTabBar={()=><FacebookTabBar tabIcons={this.tabIcons}/>}>
                <OneHome tabLabel="首页"/>
                <OneRead tabLabel="阅读"/>
                <OneMusic tabLabel="音乐"/>
                <OneFilm tabLabel="电影"/>
            </ScrollableTabView>

react-native-fs

react-native-sound

这两个主要用于one音乐的播放,其中react-native-fs主要用于音乐的下载,react-native-sound用于本地文件的播放,这两个库都用到了原生方法,因此需要分别在android和ios项目中进行设置使用:

ios端


如图需要Add两个lib的*.xcodeproj到主工程的Libraries中,然后


如图Add所有的*.a文件,编译运行就ok了。

Android 端

  1. 在setting.gradle中添加:
include ':app'
include ':react-native-fs'
project(':react-native-fs').projectDir = new File(settingsDir, '../node_modules/react-native-fs/android')
include ':RNSound', ':app'
project(':RNSound').projectDir = new File(rootProject.projectDir, '../node_modules/react-native-sound/android')
  1. 在build.gradle中添加:
    compile project(':react-native-fs')
    compile project(':RNSound')
Paste_Image.png

注意添加位置要正确,对代码进行重新编译,在Android目录机构下即可以看到RNSound、react-native-fs两个module。

两个lib在react-native 中的使用比较简单,可以参考one项目中的使用:react-native-sound 和react-native-fs的使用

项目中踩坑

  1. Image中设置source={{url:"http://..."}}
    在ios中这样设置是没有问题的,但是android中不起效, 需要设置source={{uri:"http://..."}},另关于Image,目前必须设置width和height,官方解释为防止在进行渲染时如果宽高不固定容易造成界面跳动,影响用户体验。
  2. react-native-sound 播放路径问题
var whoosh = new Sound('whoosh.mp3', Sound.MAIN_BUNDLE, (error) => {
  if (error) {
    console.log('failed to load the sound', error);
  } else { // loaded successfully
    console.log('duration in seconds: ' + whoosh.getDuration() +
        'number of channels: ' + whoosh.getNumberOfChannels());
  }
});

其中'whoosh.mp3'为相对路径,Sound.MAIN_BUNDLE为基本路径,在ios中可用,但是在android中提示找不到路径,最终第一个参数设置绝对路径,第二个参数设置为 '' 空串。

  1. react-native-sound 播放问题
musicHandler = new Sound(`${RNFS.DocumentDirectoryPath}/music.mp3`, '',(error) => {
            if (error) {
                console.log('failed to load the sound', error);
            } else { // loaded successfully
                this.playSound();
            }
        });

需要在sound创建成功的回调中启动播放,不可以直接写在创建的语句之后。

4.gif图问题
ios的Image支持直接播放gif图,android需要添加lib,在build.gradle的dependencies中添加:

compile 'com.facebook.fresco:animated-gif:0.12.0'//for gif

5.布局问题

Paste_Image.png

这种布局可以设置marginTop为负值即可。

  1. 关于react-native-viewpager和react-native-srollable-tab-view嵌套问题
    当发生嵌套时,可能发生界面的错位,这是可以设置view的style:overflow: 'hidden',可以避免界面叠加错位。

总结

目前项目中还有较多的问题,尤其是Android端,之后还会继续进行完善。根据目前的开发体验,感觉react native非常适合于展示类型的app,开发效率非常高,但是在Android上体验要低于ios,有很大的优化空间。
接下来在继续完善项目的基础上,继续学习相关的知识,争取做出自己的东西,实现在React-native项目入门与思考中立下的flag。

项目地址请戳这里

推荐阅读:

React-native项目入门与思考
React native 项目入门(知乎日报,豆瓣电影,[one]一个)
React native 项目进阶(redux, redux saga, redux logger)
React Native 项目2(One 【一个】客户端)

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 195,898评论 5 462
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 82,401评论 2 373
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 143,058评论 0 325
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 52,539评论 1 267
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 61,382评论 5 358
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 46,319评论 1 273
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 36,706评论 3 386
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 35,370评论 0 254
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 39,664评论 1 294
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 34,715评论 2 312
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 36,476评论 1 326
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 32,326评论 3 313
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 37,730评论 3 299
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,003评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,275评论 1 251
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 41,683评论 2 342
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 40,877评论 2 335

推荐阅读更多精彩内容