轉載:http://blog.csdn.net/pz789as/article/details/52537028
我們在項目裏面,經常會用的批次渲染,比如一個列表渲染很多個item,或者一個橫排或者豎排同時渲染多個數據。
例如:
- render1(){
- var arr = [];
- for(var i=0;i<5;i++){
- arr.push(
- <Text style={{fontSize:20, color: 'red'}}>
- 這是{i}
- </Text>
- );
- }
- return (
- <View style={[styles.container, styles.center]}>
- {<span style="font-family: Arial, Helvetica, sans-serif;">arr</span>}
- </View>
- );
- }
這樣寫,RN都會報一個警告,需要你對每個item添加一個key,在Text裏添加一個屬性key:
- <Text key={i} style={{fontSize:20, color: 'red'}}>
但是這個key有什麼作用呢?我們在代碼後面加一個console.log輸出一下看看結果:
- for(var i=0;i<5;i++){
- ...
- }
- console.log(arr);
看到key和那個props了嗎,我們可在未渲染之前,根據要求再次更改array裏面<Text>的屬性。我們現在來改一改試試看!
先看看上面代碼運行的效果:
然後我們在for之後這麼改看看結果如何:
- for(var i=0;i<arr.length;i++){
- if (arr[i].key == 2){
- arr[i].props.style.fontSize = 40;
- arr[i].props.style.color = 'green';
- arr[i].props.children[0] = '改變了哦';
- }
- }
結果我們可以看到,中間那個key等於2的已經改變了哦。
既然這樣,那我們繼續改一下,把這個arr改爲這個組件的一個屬性:
- constructor(props){
- super(props);
- this.state = {
- blnUpdate: false,
- };
- this.testArr = [];
- for(var i=0;i<5;i++){
- this.testArr.push(
- <Text key={i} style={{fontSize:20, color: 'red'}} onPress={this.changeChild.bind(this, i)}>
- 這是{i}
- </Text>
- );
- }
- console.log(this.testArr);
- }
另外加一個state變量,用於刷新render(爲什麼這麼做,是RN的刷新機制,需要調用this.setState纔會調用,所以弄了一個bln值,而不是把arr放在state裏面
然後在綁定還按鈕回調中這樣做:
- changeChild(key){
- console.log(key);
- if (this.testArr[key].props.children[0] == '我變了'){
- this.testArr[key].props.style = {fontSize : 20, color : 'red'};
- this.testArr[key].props.children[0] = '這是';
- }else{
- this.testArr[key].props.style = {fontSize : 30, color : 'green'};
- this.testArr[key].props.children[0] = '我變了';
- //這裏要說說text的結構,如果text是純文字,children就只有一個,如果中間夾雜着其他變量,react是將text分段保存的。
- }
- this.setUpdate();
- }
- setUpdate(){
- this.setState({
- blnUpdate: !this.state.blnUpdate
- });
- }
點擊之前:
點擊之後:
哈哈,都變了哦!!不過這樣做有點延時。其實改變渲染之後的東西,在學習RN之後會有一個專門的參數可供使用,就是每個組件的自帶屬性ref,在上面的截圖我們也看到了,現在ref是null,因爲沒有設置,如果要使用需要這樣做:
- <Text key={i} ref={'text'+i} style={{fontSize:20, color: 'red'}} onPress={this.changeChild.bind(this, i)}>
不過這個ref有個缺點,它必須要在render之後纔會產生,也就是一開始初始化後,使用this.refs.text0 會報錯,這點一定要弄清楚哦!
bind
renderAllButtons(){
var allBtns = [];
titles=['拍照','視頻','開機','照明']
for(var i=0 ;i<4;i++){
let title = titles[i];
allBtns.push(
<View key={i} style={styles.autoViewStyle}>
<TouchableOpacity style={styles.buttonStyle} onPress={this._pressBtn.bind(this,i)}>
<Text style={styles.textsStyle}>{title}</Text>
</TouchableOpacity>
</View>
);
}
_pressBtn(i){
console.log(i)
}