likes
comments
collection
share

(06)React 入门——③ 实现 TodoList 新增、删除功能 | React 基础理论实操

作者站长头像
站长
· 阅读数 31
转载请注明出处,未经同意,不可修改文章内容。

🔥🔥🔥“前端一万小时”两大明星专栏——“从零基础到轻松就业”、“前端面试刷题”,已于本月大改版,合二为一,干货满满,欢迎点击公众号菜单栏各模块了解。

涉及面试题:
1.JSX 中如何进行循环?
2. keys 是否需要全局唯一?

[编号:react_06]

1 新增

紧接上一篇的代码,我们需要实现需求:在页面 input 框里输入的内容,当点击“提交按钮”时,其内容会被依次放到下边的“列表项”里。

进入 TodoList.js 文件: 🔗前置知识:《JavaScript 基础——JS 数组:② ES5 数组方法》   《JavaScript 基础——JS 数组:① ES3 数组方法》

import React, { Component, Fragment } from "react"; 

class TodoList extends Component {
  constructor(props) {
    super(props);

    this.state = {
      inputValue: "", 
      list: ["qdywxs", "Oli", "React"] /*
      																 3️⃣-⑤:接下来,我们为了演示效果,
                                       在这里人为地写死一些内容。
                                        */
    };
  }

  render() {
    return(

      <Fragment>
        <div>
      
          <input 
            value={this.state.inputValue}
            onChange={this.handleInputChange.bind(this)}
          />

          {/*
           1️⃣既然是点击“按钮”后才有的后续一系列事,那么首先,我们得给这个“按钮”绑定一个
           “点击事件”;
            */}
          <button onClick={this.handleBtnClick.bind(this)}>
            提交
          </button>
        </div>
        <ul>
          {/*
           3️⃣-①:页面显示的内容是由“数据”决定的,所以我们先把这里为了演示而编写的初始数据注释掉;
          <li>React 初识</li>
          <li>React 入门</li>
          <li>React 进阶</li>
            */}
          
          {/* 3️⃣-②:我们把上边的“数据”项 list 显示到这里来(通过 map 方法,将每一项予以列示);*/}
          {
            this.state.list.map((item, index) => { /*
            																		 3️⃣-③:回调函数会接收两个参数:
                                                 “每一项的内容 item”和“每一项对应的下标 index”;
                                                  */
            
            	return( // 3️⃣-④:让它返回一个 li 标签,标签里展示的是“每一项的内容 item”;
              	<li>
                	{item}
              	</li>
            	)  
          	})
          }
        
        </ul>
      </Fragment>
    )
  }

  handleInputChange(e) {
    this.setState({
      inputValue: e.target.value  
    })
  }

  // 2️⃣然后,我们在这里增加点击事件执行的方法;
  handleBtnClick() {
    // 3️⃣这个方法里应该是一个怎样的逻辑呢?
    
    
  }
}

export default TodoList;

3️⃣-⑥:在页面查看效果(发现页面跟着变了); (06)React 入门——③ 实现 TodoList 新增、删除功能 | React 基础理论实操

3️⃣-⑦:既然如上图所示,效果出来了。我们需要去把 list 里边写死的内容清除掉,以便接下来的操作。

    this.state = {
      inputValue: "", 
      // list: ["qdywxs", "Oli", "React"] 
      list: []
    };

(06)React 入门——③ 实现 TodoList 新增、删除功能 | React 基础理论实操

4️⃣接下来我们实现——在页面 input 框里输入的内容,当点击“提交按钮”时,其内容会被依次放到下边的“列表项”里。

import React, { Component, Fragment } from "react"; 

class TodoList extends Component {
  constructor(props) {
    super(props);

    this.state = {
      inputValue: "", 
      list: []
    };
  }

  render() {
    return(

      <Fragment>
        <div>
      
          <input 
            value={this.state.inputValue}
            onChange={this.handleInputChange.bind(this)}
          />

          <button onClick={this.handleBtnClick.bind(this)}>
            提交
          </button>

        </div>
        <ul>
          {
            this.state.list.map((item, index) => { 
            	return( 
              	<li>
                	{item}
              	</li>
            	)  
          	})
          }
        
        </ul>
      </Fragment>
    )
  }

  handleInputChange(e) {
    this.setState({
      inputValue: e.target.value  
    })
  }

  handleBtnClick() {
    /*
    4️⃣-①:执行的方法逻辑为——将“数据”项 inputValue 里的内容,放到“数据”项 list 里。
    然后,只要“数据”项 list 里边有内容,页面就会自动变化;
     */
    this.setState({
      list: [...this.state.list, this.state.inputValue], /*
      																									 4️⃣-②:我们通过 ES6 语法,
             																						 把“新增的”和“之前的”合成一个新数组;
                                                          */
      inputValue: "" /*
      							 4️⃣-③:同时,当输入的内容展现在页面时,
                     我们把 input 框里输入的历史内容删除掉。
                      */
    })
    
  }
}

export default TodoList;

看看页面效果: (06)React 入门——③ 实现 TodoList 新增、删除功能 | React 基础理论实操

❌上图貌似完美实现了效果,但是是否有我们没有注意到的点呢? 答:有!

点开上图所在页面的控制台,我们发现了如下图所示的“警告”(不是“错误”,所以页面看起来好像一切很完美): (06)React 入门——③ 实现 TodoList 新增、删除功能 | React 基础理论实操

它提示我们:在 React 中,当你做循环渲染的时候,你需要给渲染出的每一项增加一个 key 值!这个 key 值是每一项唯一的“标识符”

就目前知识储备而言,我们先用“下标 index ”作为 key 值——当然,实际编程中,使用 index 作为 key 值是一个很不好的习惯,后边我们会详讲,这里暂时不用太过关注。 

import React, { Component, Fragment } from "react"; 

class TodoList extends Component {
  constructor(props) {
    super(props);

    this.state = {
      inputValue: "", 
      list: []
    };
  }

  render() {
    return(

      <Fragment>
        <div>
      
          <input 
            value={this.state.inputValue}
            onChange={this.handleInputChange.bind(this)}
          />

          <button onClick={this.handleBtnClick.bind(this)}>
            提交
          </button>

        </div>
        <ul>
          {
            this.state.list.map((item, index) => { 
            	return( 
              	<li key={index}>  {/* 🚀给渲染出的每一项增加一个 key 值! */}
                	{item}
              	</li>
            	)  
          	})
          }
        
        </ul>
      </Fragment>
    )
  }

  handleInputChange(e) {
    this.setState({
      inputValue: e.target.value  
    })
  }

  handleBtnClick() {
    this.setState({
      list: [...this.state.list, this.state.inputValue],  
      inputValue: ""  
    })
    
  }
}

export default TodoList;

再次查看控制台,警告没有了: (06)React 入门——③ 实现 TodoList 新增、删除功能 | React 基础理论实操

2 删除

紧接上文代码,我们需要实现新的需求:点击“列表项”里的任一项,它就会从这个列表项里被删除。

import React, { Component, Fragment } from "react"; 

class TodoList extends Component {
  constructor(props) {
    super(props);

    this.state = {
      inputValue: "", 
      list: []
    };
  }

  render() {
    return(

      <Fragment>
        <div>
      
          <input 
            value={this.state.inputValue}
            onChange={this.handleInputChange.bind(this)}
          />

          <button onClick={this.handleBtnClick.bind(this)}>
            提交
          </button>

        </div>
        <ul>
          {
            this.state.list.map((item, index) => { 
            	return( 
              
                /*
                1️⃣我们在生成 li 标签的时候,给每一个 li 标签绑定一个“点击”事件,
                使其在被“点击”时,去执行 handleItemDelete 方法;
                 */
                
                /*
                3️⃣-①:首先,我们把被“点击”的 li 的“下标”index 
                传给 handleItemDelete 方法;
                 */
              	<li 
                  key={index} 
                  onClick={this.handleItemDelete.bind(this, index)}
                >  
									{item}
              	</li>
            	)  
          	})
          }
        
        </ul>
      </Fragment>
    )
  }

  handleInputChange(e) {
    this.setState({
      inputValue: e.target.value  
    })
  }

  handleBtnClick() {
    this.setState({
      list: [...this.state.list, this.state.inputValue],  
      inputValue: ""  
    }) 
  }

	// 2️⃣我们在这里写一个 handleItemDelete 方法;
	handleItemDelete(index) { // 3️⃣-②:这里去接收到这个传递过来的“下标”;
  	
    // 3️⃣这个“删除”方法的逻辑为:
    
    const list = [...this.state.list] /*
    													3️⃣-③:我定义一个常量等于一个“拷贝”的“数据”项 list;
    													❗️❗️❗️之所以这样做,是由于 React 中有一个概念叫 immutable,
                            	它是指——state 不允许我们做任何的改变!因为它涉及到 React 性能
                            	优化相关的问题!如果你想改变,你可以“拷贝”一个副本出来进行操作。
                            					 */
    
    list.splice(index, 1) /*
    											3️⃣-④:我们用 ES3 数组里的 splice 方法,将所“点击”项删除。
    											即,所“点击”项的下标为 index,然后从 index 开始,删除 1 项。
                          ❗️splice 方法会破坏原数组,所以最后返回的是已经“删除”了某项的 list。
                           */
    
    this.setState({
      list: list // 3️⃣-⑤:再调用 setState 方法,将“数据”项 list 变为上一步得到的 list。
    }
    )
  }
}

export default TodoList;

看下页面效果:

(06)React 入门——③ 实现 TodoList 新增、删除功能 | React 基础理论实操

祝好,qdywxs ♥ you!

转载自:https://juejin.cn/post/7251407757844398117
评论
请登录