一、项目的创建
创建一个空白文件夹,打开控制台,输入命令:
npx create-react-app my-react(项目名称)
搭建一个react的脚手架,搭建完成之后输入npm my-react 进入项目
这个时候我们就可以输入npm start 启动项目了
二、修改App.js文件配置
找到项目中src文件夹中的的App.js文件,打开,然后将内容全部删除,再输入如下代码:
import React, { Component } from 'react'
export default class App extends Component {
render() {
return (
<div className="App">
</div>
)
}
}
三、创建组件
这是一个类组件,代表着App.js已经变成了一个类组件,然后在src文件夹下创建一个components文件夹,用于存放组件,并在里面创建四个文件,如下:
其中Todo.jsx为父组件,TodoInput.jsx和TodoList.jsx都是它的子组件,而todo.scss为sass样式文件,用于存放三个组件的css样式
四、App.js引入父组件
在App.js文件中将Todo.jsx文件引入,App.js代码如下:
import React, { Component } from 'react'
import Todo from "./components/Todo"
export default class App extends Component {
render() {
return (
<div className="App">
<Todo />
</div>
)
}
}
需要注意的是,引入的Tode首字母必须要大写,不然要报错。
五、Todo.jsx父组件引入子组件,并安装sass
操作步骤与App.js引入Todo.jsx组件的步骤一样,但是引入todo.sass却不需要命名,如下:
sass文件引入是不能直接使用的,需要在项目中安装才能使用,安装代码如下:
npm i node-sass@npm:dart-sass
安装完成后再启动项目就可以正常使用了
六、Todo.jsx文件代码
import React, { Component } from 'react'
import './todo.scss'
import TodoInput from './TodoInput'
import TodoList from './TodoList'
export default class Todo extends Component {
state = {
todoList: []
}
addTodo = (todo) =>{ //增加记录
const todoList = [
...this.state.todoList,
{
id:Math.random(),
body:todo,
state:false
}
]
this.setState({
todoList
})
}
//改变状态
changeState = (id) =>{
let todoList = [...this.state.todoList]
todoList.forEach(item => {
if(item.id === id){
item.state = !item.state
}
})
this.setState({
todoList
})
}
//删除记录
delTodo = (id) => {
let todoList = [...this.state.todoList]
let newtodoList = todoList.filter(item => {
return item.id !== id
}) //过滤
this.setState({
todoList:newtodoList
})
}
render() {
const {todoList} = this.state
return (
<div className="todo">
<TodoInput addTodo={this.addTodo} />
<TodoList todoList={todoList} changeState={this.changeState} delTodo={this.delTodo}/>
</div>
)
}
}
七、TodoInput.jsx文件代码
import React, { Component } from 'react'
export default class TodoInput extends Component {
state = {
todo:''
}
setTodo = (e) => {
this.setState({
todo:e.target.value
})
}
submitTodo = (e) =>{
if(e.keyCode === 13){ //判断是否按下回车
this.props.addTodo(this.state.todo)
//清空输入框的内容
this.setState({
todo:''
})
}
}
render() {
const {todo} = this.state
return (
<div className='todo-input'>
<input type="text" value={todo} onChange={this.setTodo} onKeyDown={this.submitTodo} className="todo-input-1"/>
</div>
)
}
}
八、TodoList.jsx文件代码
import React, { Component } from 'react'
export default class TodoList extends Component {
delTodo = (e,id) => {
e.preventDefault() //阻止默认事件
this.props.delTodo(id) //删除回调函数
}
changeState = (id) =>{
this.props.changeState(id)
}
render() {
const {todoList} = this.props
//列表循环
const lis = todoList.map(item => (
<li key={item.id} className='todo-item'>
<span className={['todo-select',(item.state?'done':'')].join(' ')} onClick={() => this.changeState(item.id)}></span>
<span className='todo-body'>{item.body}</span>
<a href="" onClick={(e) => this.delTodo(e,item.id)}>删除</a>
</li>
))
// 判断数据是否存在,条件渲染
const dom = todoList.length>0 ? lis : <li className="todo-li">暂无数据</li>
return (
<div className="todo-list">
<ul>
{dom}
</ul>
</div>
)
}
}
九、Todo.sass文件代码
.todo {
width: 400px;
margin: 50px auto 0;
box-shadow: 0 0 3px #dedede;
padding: 10px;
list-style-type: none;
}
.todo-li{
list-style-type: none;
}
.todo-input{
display: flex;
align-items: center;
justify-content: center;
.todo-input-1{
outline: none;
height: 30px;
padding-left: 5px;
}
}
.todo-item {
display: flex;
justify-content: space-between;
align-items: center;
height: 30px;
margin-bottom: 5px;
.todo-select {
display: inline-block;
width: 20px;
height: 20px;
background-color: #999;
}
.done {
background-color: aquamarine;
}
.todo-body {
flex: 1;
padding-left: 5px;
}
}
这样一个通过输入框输入数据,按回车后添加记录,并且点删除能删除对应记录的小demo就做好了,点击小方块还能改变记录的状态