1. 功能界面组件化流程
(1)拆分界面,抽取组件
(2) 静态页面效果
(3) 动态组件效果(动态显示初始化数据; 交互)
2. 效果
显示todo列表; 添加更新todo列表并清空input标签
3. 源码
注意点:
- 状态更新只能在初始状态对应的组件里,然后通过参数传递给需要的组件
- 逻辑复杂可以打印this查看是否有相应数据,然后再进行后续处理
- 数据传递最好检查一下数据类型
- state 数据状态位置:看哪个组件需要,如果只有单一组件需要,直接设置在那个组件上;如果有多个组件都需要的话需要将数据放在父组件上
import React, { Component } from 'react';
import PropTypes from 'prop-types';
// 父组件
class App extends Component {
constructor(){
super(...arguments)
// 设置初始化状态数据
this.state = {
todos: ['吃饭', '睡觉', '打豆豆']
}
}
// 修改状态数据,然后将函数传递给Add
addTodo = (todo)=>{
this.state.todos.unshift(todo);
this.setState({
todos: this.state.todos
})
}
render() {
return (
<div>
<h2> simple todos </h2>
<Add todoLen={this.state.todos.length} addTodo={this.addTodo} />
<List todos={this.state.todos}/>
</div>
);
}
}
// 添加组件,用于添加数据
class Add extends Component {
// 检测父组件传递过来的数据类型是否符合要求
static propTypes = {
todoLen: PropTypes.number.isRequired,
addTodo: PropTypes.func.isRequired,
}
// 点击调用父组件传过来的方法
handClick = ()=>{
console.log(this)
let todo = this.input.value.trim();
// 数据为空直接return
if(!todo) return;
// 父组件传过来的数据都存放在props里面
this.props.addTodo(todo)
this.input.value = '';
}
render() {
return (
<div>
<input type='text' ref={input=>this.input = input}/>
<button onClick={this.handClick}> add #{this.props.todoLen + 1} </button>
</div>
);
}
}
// 列表组件 用于显示
class List extends Component {
// 检测父组件传递过来的数据类型是否符合要求
static propTypes = {
todos: PropTypes.array.isRequired,
}
render() {
return (
<div>
<ul>
{
this.props.todos.map((item, index)=> <li key={index}> {item} </li> )
}
</ul>
</div>
);
}
}
export default App;