最近因為工作需要,開始學(xué)習react,在讀了基礎(chǔ)部分的文檔之后,決定寫一個todolist來練習。功能十分簡單,簡單的增加刪除。涉及到一些可以總結(jié)的部分,還是有部分涉及不到的地方,以后再談。
開始
這里我直接用了官方的cli工具create-react-app,安裝過程如下
npm install -g create-react-app
create-react-app my-app
cd my-app
npm start
index.js為入口文件,首先要引入相關(guān)的js文件
import ReactDOM from "react-dom";
import React from "react";
import "./index.css";
jsx
說到react,就不得不提到j(luò)sx,何為jsx,其實完全可以就理解為js,只不過里面有不加引號的html代碼段,舉個例子:
<li key={index}>
{li}
<span onClick={this.delList} data-id={index}>
x
</span>
</li>
這里是我return出來的語句,可以看到原來是html的部分都是那樣,在html中的{}表示的就是js的語句了。
組件
可以理解為每一個react.Component對象就是一個組件,由于js里不存在純粹意義上的class,即使是es6也只是用語法糖做了一些處理,所以定義組件有兩種寫法。
一、使用function
二、使用class
這里更推薦使用class,由于react基本就是和babel一起使用,所以學(xué)會新的方法很有必要,建議去mdn上搜索class看看文檔。
具體用法:
class XXX extends React.Component
注意要大寫,在渲染的時候在頁面中標簽也要是大寫,比如這里的<Todos/>,原因是小寫會識別為標準的html標簽
ReactDOM.render(<Todos />,document.getElementById("root"));
更多細節(jié)參考文檔,重點說明父子組件通信的問題,這里我設(shè)計了兩個組件。

父組件Todos包括確定按鈕和ul元素,子組件list則是所有列表的集合。
react有個原則是:
組件不能直接操作其它組件,而數(shù)據(jù)是從父到子單項傳遞的
這里,要說明兩個參數(shù)props,state。state表示自身可以捕捉到改變的值,props則來自于父組件。
這里我在父組件Todo里,設(shè)置了state
state = {
list: [1, 2, 3],
targetValue:'work'
};
這里面的list就是要傳遞到子組件的值,我們在子組件上定義
<List
additem={this.state.item}
tolist={this.state.list}
onChange={this.listChange}
/>
而在子組件,就可以用
this.props.tolist
獲取到list的值了,那么在父組件增加list的值,刷新state,子組件就會更新。
刪除的方法綁定在子組件上,要如何去影響父組件的list呢?
這里要使用回調(diào)了,首先在子組件的每一項上綁定相應(yīng)的方法
<span onClick={this.delList} data-id={index}>
x
</span>
然后通過props通知給父組件
delList(e) {
let index = e.target.getAttribute("data-id");
this.props.onChange(index);
}
父組件標簽部分綁定相應(yīng)的方法
<List
additem={this.state.item}
tolist={this.state.list}
onChange={this.listChange}
/>
最后在方法的部分做處理即可,完整代碼如下:
import ReactDOM from "react-dom";
import React from "react";
import "./index.css";
class List extends React.Component {
constructor(props) {
super(props);
this.delList = this.delList.bind(this);
}
delList(e) {
let index = e.target.getAttribute("data-id");
this.props.onChange(index);
}
render() {
return this.props.tolist.map((li, index) => {
return (
<li key={index}>
{li}
<span onClick={this.delList} data-id={index}>
x
</span>
</li>
);
});
}
}
class Todos extends React.Component {
constructor(props) {
super(props);
this.listChange = this.listChange.bind(this);
}
state = {
item: "xxx",
list: [1, 2, 3],
targetValue:'work'
};
listChange(index) {
let cur = this.state.list;
cur.splice(index, 1);
this.setState({ list: cur });
}
addItem(){
let value = this.state.targetValue;
let newlist = this.state.list
newlist.push(value)
this.setState({list:newlist})
}
getValue(e){
this.setState({targetValue:e.target.value})
}
render() {
return (
<div>
<input type='text' value={this.state.targetValue} onChange={this.getValue.bind(this)}/><button onClick={this.addItem.bind(this)}>確定</button>
<ul>
<List
additem={this.state.item}
tolist={this.state.list}
onChange={this.listChange}
/>
</ul>
</div>
);
}
}
ReactDOM.render(<Todos />, document.getElementById("root"));