1. 程式人生 > >React-Native之ListView的3種樣式

React-Native之ListView的3種樣式

http://www.jianshu.com/p/c52005107d81

最近在學習React-Native的ListView元件,其實ListView 相當於iOS中的tableview,當然也可以通過改變佈局來實現collectionView的樣式,和分組的tableview樣式,下面先看效果圖。


ss.gif
1,基本ListView佈局
第一種ListView佈局應該是最簡單了,沒有分組,只要知道ListView的建立方法,和如何設定  
ListView的資料來源就行了。

import React, { Component } from 'react';
import {    
    AppRegistry,    
    StyleSheet,    
    Text,    
    View
, ListView, Image} from 'react-native'; var Dimensions = require('Dimensions');//獲取螢幕的寬高 var ScreenWidth = Dimensions.get('window').width; var ScreenHeight = Dimensions.get('window').height; var FirstView = React.createClass({ getInitialState(){ var ds = new ListView.DataSource({rowHasChanged:(r1,r2) => r1 !== r2}); return
{ dataSource:ds.cloneWithRows(this.getRows({}))//初始化資料來源 } }, //製作假資料 getRows(){ var dataArr = []; for (var i = 0; i<100; i++){ dataArr.push({ title: 'Row' + i, text:'Lorem ipsum dolor sit amet, ius ad pertinax oportere accommodare, an
vix civibus corrumpit referrentur. Te nam case ludus inciderint, te mea facilisi adipiscing. Sea id integre luptatum. In tota sale consequuntur nec. Erat ocurreret mei ei. Eu paulo sapientem vulputate est, vel an accusam intellegam interesset. Nam eu stet pericula reprimique, ea vim illud modus, putant invidunt reprehendunt ne qui' + i } ) } return dataArr; }, render(){ return( // 建立ListView元件 <ListView dataSource={this.state.dataSource}//設定資料來源 renderRow={this.renderRow}//返回cell /> ) }, //返回cell的方法 renderRow(rowData,sectionID,rowID,highlightRow){ return( <View style={styles.rightViewStyle}> <Image style={styles.imageStyle}/> <View> <Text style={styles.titleStyle}>{rowData.title}</Text> <Text style={styles.textStyle}>{rowData.text}</Text> </View> </View> ) }}) //樣式 const styles = StyleSheet.create({ tabStyle:{ flex:1 }, rightViewStyle:{ flexDirection:'row', borderBottomColor:'#CCCCCC',//cell的分割線 borderBottomWidth:1 }, imageStyle:{ width:80, height:80, margin:20, backgroundColor:'red' }, titleStyle:{ marginTop:20, backgroundColor:'yellow' }, textStyle:{ width:ScreenWidth-140, backgroundColor:'green', marginBottom:20 }}); module.exports = FirstView;
2,類似collectionView的佈局
改變ListView的主軸方向,讓ListView橫向佈局,然後設定換行顯示,就能實現類似
collectionView的佈局了
import React, { Component } from 'react';
import {    
    AppRegistry,    
    StyleSheet,    
    Text,    
    View,    
    ListView,    Image} from 'react-native';

var Dimensions = require('Dimensions');//獲取螢幕的寬高
var ScreenWidth = Dimensions.get('window').width;
var ScreenHeight = Dimensions.get('window').height;

var SecondView = React.createClass({    
      getInitialState(){        
          //初始化資料來源
          var ds = new  ListView.DataSource({rowHasChanged:(r1,r2) => r1 !== r2});
          return{            
               dataSource : ds.cloneWithRows(this.getRows({}))         
          }    
      },    
      //製作假資料 
      getRows(){        
            var Arr = [];        
            for(var i = 0; i<100; i++){           
                   Arr.push(
                       {                   
                         image: '111',                   
                         price:'222'                
                      }            )        
              }        
        return Arr;    
      },    
      render(){        
          return(            
                <ListView     //建立ListView           
                      dataSource={this.state.dataSource} //設定資料來源               
                      renderRow={this.renderRow} //設定cell               
                      contentContainerStyle={styles.listViewStyle}//設定cell的樣式
              />)    
        }, 
  //返回cell的方法   
    renderRow(rowData,sectionID,rowID,highlightRow){            
        return(                
            <View style={styles.bgStyle}>                    
                <Image style={styles.imageStyle}/>                    
                <Text style={{fontSize:20,marginBottom:0}}>{rowData.price}</Text>
            </View>            )    }})
//樣式
const styles = StyleSheet.create({    
        listViewStyle:{        
              flexDirection:'row', //設定橫向佈局       
              flexWrap:'wrap'    //設定換行顯示
        },    
        bgStyle:{        
              backgroundColor:'gray',        
              width:(ScreenWidth-30)/2, //cell的寬度        
              height:250,        
              marginLeft:10,        
              marginTop:10    
        },    
        imageStyle:{        
              width:(ScreenWidth-30)/2,       
              height:230,        
              backgroundColor:'red',        
              marginBottom:0,    
      }
});
module.exports = SecondView;
3,分組ListView的佈局

5540CDF6-A572-4B35-A0DC-F827A31DBF59.png
因為是分組的ListView,顯然設定資料來源的方法就應該用cloneWithRowsAndSections

import React, { Component } from 'react';
import {    
    AppRegistry,    
    StyleSheet,    
    Text,    
    View,    
    ListView,    
    Image} from 'react-native';

如果不提供針對section標題和行資料提供自定義的提取方法,就會使用預設的方法,


98293E7A-C6BB-4D20-9E05-53BB2EE8A6C9.png
var ThirdView = React.createClass({    
      getInitialState(){        
          var getSectionData = (dataBlob,sectionID)=>{            
                return dataBlob[sectionID];        
          };        
          var getRowData = (dataBlob,sectionID,rowID) =>{            
                  return dataBlob[sectionID + ':' + rowID];        
          };
          因為這裡我們需要返回區的資料,所以我們需要提供方法來提取行資料和section標題        
          return{            
              dataSource:new ListView.DataSource({                                     
              getSectionData:getSectionData,                
              getRowData:getRowData,                
              rowHasChanged:(r1,r2)=> r1 !==r2,                
              sectionHeaderHasChanged:(s1,s2)=> s1!== s2            })        }    
},

F2E6FFB0-D204-4F5E-8BB6-AB3C6BE0EBA9.png
//從上面的圖片我們可以看出提取函式處理的資料的形式,其實就是個二維陣列,
//製作假資料        
getLocaData(){
      var  Arr = {},            
      sectionIDs =[],//所有區ID的陣列            
      rowIDs =[];//行ID陣列
       //通過兩次for迴圈建立假資料      
      for (var i = 0; i< 10; i++){           
           sectionIDs.push(i);            
           Arr[i] = 'section' + i;            
           rowIDs[i] = [];            
          for (var j= 0; j<5; j++){                
                rowIDs[i].push(j);                
                Arr[i +':' +j] = 'section' + i + '--row' + j;           
           }       
       } 
    //重新設定ListView的資料來源,重新整理表       
    this.setState({      
       dataSource:this.state.dataSource.cloneWithRowsAndSections(Arr,sectionIDs,rowIDs)            
  })    
},    
render(){        
      return(            
            <ListView//建立表,並設定返回section和cell的方法                
                    dataSource={this.state.dataSource}                
                    renderRow={this.renderRow}                
                    renderSectionHeader={this.renderSectionHeader}                                
                    contentContainerStyle={styles.listViewStyle}            />        )    
},    
//這個方法相當於iOS的viewDidload方法,通常用於網路請求,返回資料之後重新重新整理表,這裡讓它呼叫製作假資料的方法,然後重新整理表    
componentDidMount(){         
    this.getLocaData();    
},  
//返回cell的方法  
renderRow(rowData,sectionID,rowID,highlighRow){        
      return(            
              <View style={styles.cellStyle}>                
                  <Image style={styles.imageStyle}/>                
                  <Text>{rowData}</Text>            
              </View>        )    
}, 
//返回section的方法  
renderSectionHeader(sectionData,sectionID){        
      return(            
            <View style={styles.sectionStyle}>                
                <Text>{sectionData}</Text>            
           </View>        )    },})
//樣式
const styles = StyleSheet.create({    
          sectionStyle:{        
                backgroundColor:'gray',        
                height:25    
          },    
        cellStyle:{        
              flexDirection:'row', //設定橫向佈局       
              borderBottomColor:'#CCCCCC',        
              borderBottomWidth:1,        
              alignItems:'center'//交叉軸的對齊方式    
         },    
        imageStyle:{        
              width:70,        
              height:70,        
              backgroundColor:'red',        
              margin:20    
        },
});
module.exports = ThirdView;

最後的樣子就是下面的圖片,主要要理解ListView的資料來源的結構,通過構造假資料可以更好的理解如何給ListView設定資料來源


2FA7116E-088F-4A51-9F1B-0AF3CDCF5FC4.png