国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁(yè) > 學(xué)院 > 開(kāi)發(fā)設(shè)計(jì) > 正文

React-Native牛刀小試仿京東砍啊砍砍到你手軟

2019-11-14 18:03:34
字體:
來(lái)源:轉(zhuǎn)載
供稿:網(wǎng)友

React-Native牛刀小試仿京東砍啊砍砍到你手軟

React-Native基礎(chǔ)教程

*React-Native基礎(chǔ)篇作者git

*React-Native官方文檔

*Demo

    幾個(gè)月前facebook推出了React Native框架,允許開(kāi)發(fā)著使用javascript代碼來(lái)實(shí)現(xiàn)iOS原生的應(yīng)用,隨后十月份安卓版的也相繼問(wèn)世,從此我們可以?xún)?yōu)雅的Learn once, write anywhere…

    早在幾年前開(kāi)發(fā)者就開(kāi)始使用Javascript+html和PhoneGap來(lái)編寫(xiě)各式各樣的app了,開(kāi)發(fā)者可以?xún)?yōu)雅的完成一套js的shell,然后分別在不同的平臺(tái)下進(jìn)行打包,最終生成不同平臺(tái)的app,知識(shí)app的最終的展現(xiàn)形式都是html類(lèi)型的。一度曾經(jīng)出現(xiàn)webapp 是否要取代native ,這么多年過(guò)去,結(jié)果大家也不言而知了。

    但是react native的確是一個(gè)很了不起的東西,開(kāi)發(fā)者們都不禁為之歡呼,react native所展現(xiàn)出來(lái)的應(yīng)用實(shí)質(zhì)上是native應(yīng)用,開(kāi)發(fā)者完成同一套js代碼,分別在iOS和安卓平臺(tái)下分別打包最終分別能映射生成分屬不同的安卓原生應(yīng)用與iOS原生應(yīng)用,這個(gè)優(yōu)勢(shì)可能是目前為止被廣大開(kāi)發(fā)最為喜歡的地方,一直以來(lái)web app最為大家所詬病的可能就是html的頁(yè)面永遠(yuǎn)無(wú)法與原生頁(yè)面的體驗(yàn)相比擬。

  • 通過(guò)react native框架,你可以用JavaScript來(lái)編寫(xiě)和運(yùn)行應(yīng)用程序邏輯,而UI卻可以是真正的本地代碼編寫(xiě)的,因此,你完全不需要一個(gè)HTML5編寫(xiě)的UI。

  • React框架采用了一種新穎的、激進(jìn)的和高度函數(shù)式的方式來(lái)構(gòu)建UI。簡(jiǎn)單說(shuō),應(yīng)用程序的UI可以簡(jiǎn)單地用一個(gè)函數(shù)來(lái)表示應(yīng)用程序當(dāng)前的狀態(tài)

    React Native的重點(diǎn)是把React編程模型引進(jìn)到移動(dòng)App的開(kāi)發(fā)中去。它的目的并不是跨平臺(tái),一次編寫(xiě)到處運(yùn)行。它真正的目標(biāo)是“一次學(xué)習(xí)多處編寫(xiě)”。這是一個(gè)重大的區(qū)別。本教程只涉及iOS,但一旦你學(xué)會(huì)了它的思想,你就可以快速將同樣的知識(shí)應(yīng)用到Android App的編寫(xiě)上。

    React Native的編寫(xiě)模式更加友好于從事于js的前端開(kāi)發(fā)者,它本身采用了React js的模式,尤其是從事React js的開(kāi)發(fā)人員,只需要熟悉下基本的文檔就能瞬間變成一個(gè)iOS+安卓雙向通吃的移動(dòng)專(zhuān)家,React內(nèi)部引入可一些新的概念,如 DOM和reconciliation,React直接將函數(shù)式編程的理念用到了UI層面。
不過(guò)相對(duì)來(lái)說(shuō),OC的開(kāi)發(fā)人員只要熟悉一下基本demo看上幾個(gè)例子應(yīng)該就不會(huì)有太多問(wèn)題了,如果之前有過(guò)web端開(kāi)發(fā)經(jīng)驗(yàn)的話相信上手會(huì)更快一些。

下面介紹一個(gè)簡(jiǎn)單的demo操作,這個(gè)教程一起帶你去體驗(yàn)一下京東促銷(xiāo)砍啊砍頁(yè)面的OC->React 移植過(guò)程,通過(guò)本教程你就可以了解React Native的一些基本開(kāi)發(fā)流程了。
效果:

如果你之前從未寫(xiě)過(guò)任何 JavaScript ,別擔(dān)心;這篇教程帶著你一點(diǎn)一點(diǎn)編寫(xiě)代碼。React 使用 CSS 屬性來(lái)定義樣式,這些樣式通常都很易于閱讀和理解,但是如果你想進(jìn)一步了解,可以參考:。
要想學(xué)習(xí)更多內(nèi)容,請(qǐng)往下看

開(kāi)始

React native 關(guān)于環(huán)境搭建問(wèn)題此處就不多說(shuō)了,詳情請(qǐng)見(jiàn)React native基礎(chǔ)教程,此處就從我們已經(jīng)準(zhǔn)備好一切前序工作開(kāi)始,萬(wàn)事具備只欠東風(fēng),下面開(kāi)始:

首先React Native 啟動(dòng)畫(huà)面開(kāi)始,創(chuàng)建helloworld工程,啟動(dòng)畫(huà)面如下:

與此同時(shí)Xcode還會(huì)打開(kāi)一個(gè)終端窗口,并顯示如下信息:

這是React Navtive Packager,它在node容器中運(yùn)行。你待會(huì)就會(huì)發(fā)現(xiàn)它的用處。
千萬(wàn)不要關(guān)閉這個(gè)窗口,讓它一直運(yùn)行在后面。如果你意外關(guān)閉它,可以在Xcode中先停止程序,再重新運(yùn)行程序。

注意:

  • 在開(kāi)始接觸具體的代碼之前(在本教程中,主要是js代碼),我們將推薦 Sublime
  • Text這個(gè)文本編輯工具,因?yàn)閄code并不適合用于編寫(xiě)js代碼的。當(dāng)然,你也可以使用 atom, brackets
  • 等其他輕量級(jí)的工具來(lái)替代。

 

React Native完成的js完成的代碼其實(shí)是跑在本地的node下面的,從appdelegate里面可以看到React Native工程會(huì)從一個(gè)本機(jī)地址“http://localhost:8081/index.ios.bundle?platform=ios&dev=true”讀取一個(gè)對(duì)應(yīng)的文件,這個(gè)文件中就是系統(tǒng)已經(jīng)自動(dòng)幫你打包壓縮整合過(guò)以后的一個(gè)js 代碼庫(kù),接下來(lái)React Native引擎會(huì)將這個(gè)庫(kù)中的js代碼完全的解析、翻譯成對(duì)應(yīng)的iOS原生內(nèi)容,最終以iOS原生UI的形式渲染到桌面上,這個(gè)就是React Native整個(gè)工作流程。

你好, React Native

在開(kāi)始編寫(xiě)這個(gè)demo之前我們先創(chuàng)建一個(gè)簡(jiǎn)單的Hello World項(xiàng)目,用你喜歡的文本編輯器(例如Sublime Text)打開(kāi)index.ios.js ,刪除所有內(nèi)容。然后加入以下語(yǔ)句:

'use strict';var React = require('react-native');var {  ApPRegistry,  Text,  View,} = React;var HelloWorld = React.createClass({  render: function() {    return (      <View>        <View><Text>你好, React Native</Text></View>       </View>    );  }});AppRegistry.registerComponent('HelloWorld', () => HelloWorld);

好了,“Hello World” 的演示就到此為止;接下來(lái)我們要編寫(xiě)一個(gè)真正的React App了!

創(chuàng)建一個(gè)導(dǎo)航

這個(gè)demo使用了標(biāo)準(zhǔn)的UIKit中的導(dǎo)航控制器來(lái)提供”棧式導(dǎo)航體驗(yàn)“。接下來(lái)我們就來(lái)實(shí)現(xiàn)這個(gè)功能。

在 index.ios.js, 添加以下代碼:

var Home = require('./cut/Home');var HelloWorld = React.createClass(//{  render: function() //{    return (      <NavigatorIOS              initialRoute=//{//{title:'首頁(yè)',                        component:Home,                      //}//}//>    );  //}//});

NavigatorIOS就是React Native中對(duì)應(yīng)的導(dǎo)航視圖,我們?cè)俅螘簳r(shí)可以理解就是iOS中的UINavigationController,我們?cè)诖颂巹?chuàng)建了一個(gè)基于導(dǎo)航的視圖控制器,rootViewController對(duì)應(yīng)的頁(yè)面就是Home。

創(chuàng)建rootView Home,添加Home.js 文件,添加代碼如下:

var cutList = require('./CutList');var Home = React.createClass({	render:function (){		return (			<TouchableHighlight onPress={()=> this.goToNext()}>			<View>				<Text}>go to cut</Text>			</View>			</TouchableHighlight>          );	},	goToNext:function(){		this.props.navigator.push({      		component: cutList,    });	},});

Home 我們只放了一個(gè)按鈕,按鈕文字“go to cut”,另外添加了一個(gè)點(diǎn)擊觸摸事件,事件相應(yīng)題是goToNext:function(); 在函數(shù)處理事件內(nèi)部,我們只做了頁(yè)面的push跳轉(zhuǎn),目標(biāo)頁(yè)面是cutList頁(yè)面,運(yùn)行效果如下:

構(gòu)建砍啊砍List頁(yè)面,從網(wǎng)絡(luò)獲取數(shù)據(jù),繪制table綁定事件

構(gòu)造頂部bunner動(dòng)畫(huà)圖

輪播圖這個(gè)地方采用了React Native的一個(gè)第三方庫(kù)swiper(偷懶了),

var Swiper = require('react-native-swiper');初始化數(shù)據(jù)var sliderImgs = [    'http://m.360buyimg.com/mobile/s725x175_jfs/t2332/80/701506039/111191/37a1273/5624850bN2469d61f.jpg',    'http://m.360buyimg.com/mobile/s725x175_jfs/t2401/354/694665708/117887/3a283185/56248ee2N58518e76.jpg',    'http://m.360buyimg.com/mobile/s725x175_jfs/t2506/269/651438394/152836/cf430d42/561f6b3aN80cb83f4.jpg',    'http://m.360buyimg.com/mobilecms/s750x410_jfs/t2326/263/687562306/170970/c3f92c7/5620cbddNaa6a2cda.jpg!q70.jpg',    'http://m.360buyimg.com/mobilecms/s750x410_jfs/t1891/237/637408747/193879/1acee0f7/5620be19N801621e4.jpg!q70.jpg'];//初始化UIrender:function () //{		return (			<View>				<View>					<Swiper style=//{styles.wrapper//} showsButtons=//{false//} autoplay=//{true//} height=//{150//} showsPagination={true}>        				<Image style={[styles.slide,]} source=></Image>        				<Image style={[styles.slide,]} source=></Image>        				<Image style={[styles.slide,]} source=></Image>        				<Image style={[styles.slide,]} source=></Image>        				<Image style={[styles.slide,]} source=></Image>      				</Swiper>				</View>				<View style={styles.listViewSuper}>					<ListView style={styles.tableStyle}          				dataSource = {this.state.dataSource}          				renderRow={this._renderRow.bind(this)}                  pageSize={5}                  automaticallyAdjustContentInsets={false}//>				</View>			</View>			);	},

再次看到render:function()這個(gè)函數(shù),應(yīng)該沒(méi)那么陌生了吧,暫時(shí)可以理解render相當(dāng)于ViewController中的ViewDidLoad:,我們一般在render里面做一些初始化UI視圖的工作,此處我們初始化了swiper和ListView

swiper

  • showsButtons        (bool)   是否顯示左右切換按鈕(顯示兩個(gè)按鈕左切 友切)
  • autoplay                (bool)   是否開(kāi)啟自動(dòng)播放
  • height                    (bool)    高度(不解釋)
  • showsPagination  (bool)   是否顯示pageControl

ListView

  •  dataSource 綁定數(shù)據(jù)源
  •  renderRow cell綁定函數(shù)事件(等價(jià)于tableView:cellForRowAtIndexPath:)
  •  automaticallyAdjustContentInsets UI布局相關(guān)的

 

初始化數(shù)據(jù)源

getInitialState:function(){      var ds = new ListView.DataSource({rowHasChanged: (r1, r2) => r1 !== r2});      return {        dataSource: new ListView.DataSource({        	rowHasChanged: (r1, r2) => r1 !== r2        }),        loaded:false,        currentPage:0,      };  	}

getInitialState:function()類(lèi)似于OC中的init函數(shù),我們一般的習(xí)慣喜歡在init函數(shù)初始化一個(gè)變量等數(shù)據(jù),在React Native依舊是這樣。

發(fā)起網(wǎng)絡(luò)請(qǐng)求,獲取數(shù)據(jù),緩存在全局變量List中

//定義request url var urlPath = 'http://ccguo.gitcafe.io/cut.json';var CACHE = [];//componentDidMount:function  系統(tǒng)方法componentDidMount:function(){  		this.fetchData();  	},//自定義函數(shù)處理網(wǎng)絡(luò)獲取數(shù)據(jù),將數(shù)據(jù)放入全局變量CACHE  	cache:function(items){      for (var i in items) {        CACHE.push(items[i]);      }      this.setState({               dataSource: this.state.dataSource.cloneWithRows(CACHE),        });    },//發(fā)起 網(wǎng)絡(luò)請(qǐng)求,獲得json  	fetchData:function(){      console.log('hello world');  		fetch(urlPath)  		  .then((response) => response.json())        .then((responseText) => {          console.log(responseText.cutList);          this.cache(responseText.cutList);        })        .catch((error) => {          console.log(error);        });  	}

    這個(gè)過(guò)程模擬了在iOS原生應(yīng)用里面,初始化網(wǎng)絡(luò)request,發(fā)起網(wǎng)絡(luò)請(qǐng)求,得到數(shù)據(jù),解析數(shù)據(jù),然后將數(shù)據(jù)存入list這一些列操作,其實(shí)在js中,js腳本處理json的能力還是很強(qiáng)的,我們?cè)僖膊恍枰馩C中哪些objectForKey:的操作了,我們不需要任何MJExtension、JSONModel、 Mantle等一些潛在的工具了,省去了很多的麻煩,我們直接拿到一個(gè)json對(duì)象,直接對(duì)對(duì)象進(jìn)行操作。

    另外React的網(wǎng)絡(luò)請(qǐng)求此處我們只是使用了fetch API
臉譜官方的api(臉譜對(duì)于網(wǎng)絡(luò)請(qǐng)求提供了多種API,如:fetch WebSocket xmlHttpRequest等,具體可參照API)

    從代碼上看js的鏈?zhǔn)骄幊虅偪瓷先ビ悬c(diǎn)不太習(xí)慣,不過(guò)整體使用起來(lái)還是比OC中快捷多了,foreach遍歷、消息隊(duì)列進(jìn)出棧,總之腳步里面省去了以往還不得不在意的好多麻煩,其實(shí)這塊相對(duì)swift而言,新的版本中漸漸的已經(jīng)得到了部分提升,不過(guò)還是要感謝臉譜團(tuán)隊(duì),沒(méi)有他們,可能還見(jiàn)識(shí)不到React的強(qiáng)大。

構(gòu)建cell

	_renderRow:function(data,sectionID,rowID){    return (      <TouchableHighlight onPress={() => this._pressRow(data,rowID)}>      <View style=>        <View style=>          <View style=>              <Image style= source=></Image>          </View>          <View style={styles.row,{flex:3,borderColor:'blue',borderWidth:0.5}}>            <Text style=>              {rowID+'-'+data.wname}            </Text>            <Text style=>京東價(jià)318.00</Text>            <View style=>            <Text style=>已有256人砍價(jià)</Text>            <Text style=>馬上砍</Text>            </View>          </View>        </View>          <View style={styles.separator} />      </View>        </TouchableHighlight>      );  },  _pressRow: function(data,rowID) {    this.props.navigator.push({      component: detail,      passProps: {data: data}    });  }

在上述初始化ListView UI的時(shí)間,我們指定了renderRow 對(duì)應(yīng)的action事件,此處我們可以直接在_renderRow:function中構(gòu)建自己的cell模版,至于React Native中UI的標(biāo)簽基本用法,大家可以去頭部基礎(chǔ)教程里面找,有點(diǎn)類(lèi)似于html標(biāo)簽,總之我們?cè)赺renderRow:function純碎是構(gòu)造cell的代碼,這個(gè)類(lèi)似于tableViewCell subClass, cell點(diǎn)擊事件我們使用一個(gè)TouchableHighlight來(lái)代替

 <TouchableHighlight onPress={() => this._pressRow(data,rowID)}> .... </TouchableHighlight>

TouchableHighlight事件處理action同樣是一個(gè)函數(shù)(不解釋?zhuān)赺pressRow事件中我們處理自己的cell點(diǎn)擊跳轉(zhuǎn),順便插一句下一步的操作,_pressRow(data,rowID)是帶有形參的
另外 ListView renderRow 事件的重載函數(shù),形參類(lèi)型這個(gè)具體參照臉譜官方的api

_renderRow:function(data,sectionID,rowID)。

整體運(yùn)行效果如下:

處理cell跳轉(zhuǎn)事件

var detail = require('./Detail'); _pressRow: function(data,rowID) {    this.props.navigator.push({      component: detail,      passProps: {data: data}    });  }

React在處理事件跳轉(zhuǎn)的時(shí)間,仍舊采用進(jìn)棧出棧的形式,這一點(diǎn)和Apple的理念還是類(lèi)似的。

  • component:     參數(shù)對(duì)應(yīng)將要跳轉(zhuǎn)的目標(biāo)頁(yè)面,
  • passProps:     傳參字典,內(nèi)部為key-val形式,相當(dāng)于一個(gè)容器,到了目標(biāo)頁(yè)面后可以根據(jù)key從容器中取出傳遞的值。

獲取頁(yè)面跳轉(zhuǎn)時(shí)間容器中的值

<Text style={styles.view}>{this.props.data.wname}</Text>

到了目標(biāo)頁(yè)面后,我們直接從props容器直接根據(jù)key就能將傳遞的參數(shù)去處,此處我們傳遞參數(shù)的本身是一個(gè)json,我們只是講wname顯示到detail頁(yè)面。
效果如下:

接下來(lái)做什么

恭喜你,你的第一個(gè)React Native App終于完成了!你可以在GitHub上找到每一個(gè)”可運(yùn)行的“步驟的項(xiàng)目源文件,如果你搞不定的時(shí)候它們會(huì)非常有用的 :]

如果你來(lái)自Web領(lǐng)域,你可能覺(jué)得在代碼中用JS和React框架建立基于本地化UI的App的界面并實(shí)現(xiàn)導(dǎo)航不過(guò)是小菜一碟。但如果你主要開(kāi)發(fā)的是本地App,我希望你能從中感受到React Native的優(yōu)點(diǎn):快速的App迭代,現(xiàn)代JavaScript語(yǔ)法的支持和清晰的CSS樣式規(guī)則。

在你的下一個(gè)App中,你是會(huì)使用這個(gè)框架,還是會(huì)繼續(xù)頑固不化地使用Swift和O-C呢?

無(wú)論你怎么選擇,我都希望你能從本文的介紹中學(xué)習(xí)到一些有趣的新東西,并把其中一些原理應(yīng)用到你的下一個(gè)項(xiàng)目中。

如果你有任何問(wèn)題及建議,請(qǐng)參與到下面的討論中來(lái)!


發(fā)表評(píng)論 共有條評(píng)論
用戶名: 密碼:
驗(yàn)證碼: 匿名發(fā)表
主站蜘蛛池模板: 正宁县| 延吉市| 潼关县| 泰顺县| 北碚区| 广宗县| 塘沽区| 贺州市| 邛崃市| 桦甸市| 随州市| 沽源县| 周口市| 沙田区| 绥滨县| 平顶山市| 富锦市| 田阳县| 达州市| 边坝县| 关岭| 拜城县| 泾川县| 凭祥市| 乐安县| 三明市| 五河县| 合水县| 桂阳县| 威海市| 文水县| 青铜峡市| 宁阳县| 革吉县| 外汇| 霞浦县| 双桥区| 遂川县| 芜湖市| 庆城县| 诸暨市|