CRUD案例
import './index.css' import avatar from './images/avatar.png' import React from 'react' import { v4 as uuid } from 'uuid' // 时间格式化 function formatDate (time) { return `${time.getFullYear()}-${time.getMonth()}-${time.getDate()}` } class App extends React.Component { state = { // hot: 热度排序 time: 时间排序 active: 'hot', // 控制tab激活的关键状态 tabs: [ { id: 1, name: '热度', type: 'hot' }, { id: 2, name: '时间', type: 'time' } ], list: [ { id: 1, author: '刘德华', comment: '给我一杯忘情水', time: new Date('2021-10-10 09:09:00'), // 1: 点赞 0:无态度 -1:踩 attitude: 1 }, { id: 2, author: '周杰伦', comment: '哎哟,不错哦', time: new Date('2021-10-11 09:09:00'), // 1: 点赞 0:无态度 -1:踩 attitude: 0 }, { id: 3, author: '五月天', comment: '不打扰,是我的温柔', time: new Date('2021-10-11 10:09:00'), // 1: 点赞 0:无态度 -1:踩 attitude: -1 } ], comment: '', // 评论中的内容 } // tab切换回调 switchTab = (type) => { this.setState({ active: type }) } render () { return ( <div className="App"> <div className="comment-container"> {/* 评论数 */} <div className="comment-head"> <span>5 评论</span> </div> {/* 排序 */} <div className="tabs-order"> <ul className="sort-container"> { this.state.tabs.map(tab => ( <li onClick={() => { this.switchTab(tab.type) }} key={tab.id} className={tab.type === this.state.active ? 'on' : ''} >按{tab.name}排序</li> )) } </ul> </div> {/* 当前项的type值和记录下来的type值进行比对 */} {/* 添加评论 */} <div className="comment-send"> <div className="user-face"> <img className="user-head" src={avatar} alt="" /> </div> <div className="textarea-container"> {/* 输入框 受控组件的方式拿到输入框中的数据 */} <textarea cols="80" rows="5" placeholder="发条友善的评论" className="ipt-txt" value={this.state.comment} onChange={this.textareaChange} /> <button className="comment-submit" onClick={this.pubComment}>发表评论</button> </div> <div className="comment-emoji"> <i className="face"></i> <span className="text">表情</span> </div> </div> {/* 评论列表 */} <div className="comment-list"> { this.state.list.map((item) => ( <div className="list-item" key={item.id}> <div className="user-face"> <img className="user-head" src={avatar} alt="" /> </div> <div className="comment"> <div className="user">{item.author}</div> <p className="text">{item.comment}</p> <div className="info"> <span className="time">{formatDate(item.time)}</span> <span onClick={() => this.toggleLike(item)} className={item.attitude === 1 ? 'like liked' : 'like'}> <i className="icon" /> </span> <span className={item.attitude === -1 ? 'hate hated' : 'hate'}> <i className="icon" /> </span> <span className="reply btn-hover" onClick={() => { this.deleteComment(item.id) }}>删除</span> </div> </div> </div> )) } </div> </div> </div>) } // 受控组件的回调 textareaChange = (e) => { this.setState({ comment: e.target.value }) } // 发表评论 pubComment = (e) => { // 提交评论 if (!this.state.comment.length) { return } this.setState({ list: [ ...this.state.list, { id: uuid(), // 唯一性 author: '斯皮尔伯格', comment: this.state.comment, time: new Date(), // 1: 点赞 0:无态度 -1:踩 attitude: 0 }, ] }) } // 删除评论(根据id删除评论) deleteComment = (id) => { console.log(`id: ${id}`) this.setState({ list: this.state.list.filter(item => item.id != id), }) } // 切换喜欢 toggleLike = (curItem) => { // Logic: 若1就改为0,否则改为1 - attitude console.log(`curItem: ${JSON.stringify(curItem)}`) const { attitude, id } = curItem this.setState({ list: this.state.list.map(item => { // 判断条件 如果item.id === id 则把item的attitude修改 // 否则跳过 if (item.id === id) { return { ...item, // 当属性发生重复会进行覆盖 attitude: attitude === 1 ? 0 : 1, } } else { return item } }) }) } } export default App ···
学而不思则罔,思而不学则殆!
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· winform 绘制太阳,地球,月球 运作规律
· 超详细:普通电脑也行Windows部署deepseek R1训练数据并当服务器共享给他人
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· AI 智能体引爆开源社区「GitHub 热点速览」
· 写一个简单的SQL生成工具
2021-03-19 Error response from daemon: dockerfile parse error line 1: FROM requires either one or three arguments [Docker利用Dockerfile构建镜像出错]