Todo-List案例版本一

初级使用e.target.value 

记得安装npm i nanoid与UUID类似 快捷键ctrl+H替换内容

src/components/MyHeader.vue

<template><div class="todo-header"><input type="text" placeholder="请输入你的任务名称,按回车键确认" v-model="title" @keyup.enter="add()" /></div>
</template><script>
import {nanoid} from 'nanoid'
export default {name: 'MyHeader',data(){return{title:''}},props:['addToDo'],methods:{add(){if(!this.title.trim()) return alert('输入不能为空!')// 给用户输入的内容包装成一个todoObj对象const todoObj={id:nanoid(),title:this.title,done:false};this.addToDo(todoObj);this.title='';}}
}
</script><style scoped>
/*header*/
.todo-header input {width: 560px;height: 28px;font-size: 14px;border: 1px solid #ccc;border-radius: 4px;padding: 4px 7px;
}.todo-header input:focus {outline: none;border-color: rgba(82, 168, 236, 0.8);box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 8px rgba(82, 168, 236, 0.6);
}
</style>

src/components/MyList.vue

<template><ul class="todo-main"><MyItemv-for="todoObj in todos" :key="todoObj.id" :todo="todoObj" :checkTodo="checkTodo":deleteTodo="deleteTodo"/></ul>
</template><script>
import MyItem from './MyItem.vue'export default {name: 'MyList',props:['todos','checkTodo','deleteTodo'],components: { MyItem }
}
</script><style scoped>
/*main*/
.todo-main {margin-left: 0px;border: 1px solid #ddd;border-radius: 2px;padding: 0px;
}.todo-empty {height: 40px;line-height: 40px;border: 1px solid #ddd;border-radius: 2px;padding-left: 5px;margin-top: 10px;
}
</style>

src/components/MyItem.vue

<template><li><label><input type="checkbox" :checked="todo.done" @change="handleCheck(todo.id)" /><!-- 以下代码也能实现功能,但是不太推荐,因为有点违反规则,因为修改了props,只不过vue没有监测到(vue监测到的情况是对象全部被变化 --><!-- <input type="checkbox" v-model="todo.done"/> --><span>{{ todo.title }}</span></label><button class="btn btn-danger" @click="handleDelete(todo.id)">删除</button></li>
</template><script>
export default {name: 'MyItem',//声明接收todo对象props: ['todo', 'checkTodo','deleteTodo'],methods: {handleCheck(id) {// 通知App组件将对应的todo对象的done值取反// console.log(id);this.checkTodo(id)},handleDelete(id){if(confirm('确定删除吗?')){this.deleteTodo(id)}}}
}
</script><style scoped>
/*item*/
li {list-style: none;height: 36px;line-height: 36px;padding: 0 5px;border-bottom: 1px solid #ddd;
}li label {float: left;cursor: pointer;
}li label li input {vertical-align: middle;margin-right: 6px;position: relative;top: -1px;
}li button {float: right;display: none;margin-top: 3px;
}li:before {content: initial;
}li:last-child {border-bottom: none;
}li:hover {background-color: #ddd;
}li:hover button {display: block;
}
</style>

src/components/MyFooter.vue 

<template><div class="todo-footer" v-show="total"><label><!-- <input type="checkbox" :checked="isAll" @change="checkAll"/> --><input type="checkbox" v-model="isAll"/></label><span><span>已完成{{ doneTotal }}</span> / 全部{{ total }}</span><button class="btn btn-danger" @click="clearAll">清除已完成任务</button></div>
</template><script>
export default {name: 'MyFooter',props: ['todos','checkAllTodo','clearAllTodo'],computed: {total() {return this.todos.length},doneTotal() {// 数组.reduce()方法// const x = this.todos.reduce((pre, cur) => {//     return pre + (cur.done ? 1 : 0)// }, 0)// return xreturn this.todos.reduce((pre, todo) => pre + (todo.done ? 1 : 0), 0)},// 计算属性简写版// isAll() {//     return this.doneTotal === this.total && this.total > 0// }// 计算属性完整版isAll:{get(){return this.doneTotal === this.total && this.total > 0},set(value){this.checkAllTodo(value);}}},// methods:{//     checkAll(e){//         // console.log(e.target.checked);//         this.checkAllTodo(e.target.checked);//     }// }methods:{clearAll(){this.clearAllTodo()}}
}
</script><style scoped>
/*footer*/
.todo-footer {height: 40px;line-height: 40px;padding-left: 6px;margin-top: 5px;
}.todo-footer label {display: inline-block;margin-right: 20px;cursor: pointer;
}.todo-footer label input {position: relative;top: -1px;vertical-align: middle;margin-right: 5px;
}.todo-footer button {float: right;margin-top: 5px;
}
</style>

src/App.vue

<template><div id="root"><div class="todo-container"><div class="todo-wrap"><MyHeader :addToDo="addToDo"/><MyList :todos="todos" :checkTodo="checkTodo" :deleteTodo="deleteTodo"/><MyFooter :todos="todos" :checkAllTodo="checkAllTodo" :clearAllTodo="clearAllTodo"/></div></div></div>
</template><script>
import MyHeader from './components/MyHeader'
import MyList from './components/MyList'
import MyFooter from './components/MyFooter'export default {name: 'App',data() {return {todos: [{ id: '001', title: '抽烟', done: true },{ id: '002', title: '喝酒', done: false },{ id: '003', title: '开车', done: true }]}},components: { MyHeader, MyList, MyFooter },methods:{// 添加一个todoaddToDo(todoObj){this.todos.unshift(todoObj)},// 勾选or取消勾选一个todocheckTodo(id){this.todos.forEach((todo)=>{if(todo.id===id) todo.done=!todo.done})},// 删除一个tododeleteTodo(id){// 注意:filter不改变原数组,只是新建一个数组this.todos=this.todos.filter((todo)=>{return todo.id!==id})},// 全选or取消全选checkAllTodo(done){this.todos.forEach((todo)=>{todo.done=done})},// 清除所有已完成的todoclearAllTodo(){this.todos=this.todos.filter((todo)=>{return !todo.done})}}
}
</script><style>
/*base*/
body {background: #fff;
}.btn {display: inline-block;padding: 4px 12px;margin-bottom: 0;font-size: 14px;line-height: 20px;text-align: center;vertical-align: middle;cursor: pointer;box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.2), 0 1px 2px rgba(0, 0, 0, 0.05);border-radius: 4px;
}.btn-danger {color: #fff;background-color: #da4f49;border: 1px solid #bd362f;
}.btn-danger:hover {color: #fff;background-color: #bd362f;
}.btn:focus {outline: none;
}.todo-container {width: 600px;margin: 0 auto;
}.todo-container .todo-wrap {padding: 10px;border: 1px solid #ddd;border-radius: 5px;
}
</style>

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/13211.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

浅谈RPC协议

RPC协议 RPC简介为啥需要RPCRPC的调用过程gRPCProtoBuffergRPC实战 RPC简介 RPC&#xff08;Remote Procedure Call Protocol&#xff09;远程过程调用协议&#xff0c;目标就是让远程服务调用更加简单、透明。RPC 框架负责屏蔽底层的传输方式&#xff08;TCP 或者 UDP&#x…

《动手学深度学习》——线性神经网络

参考资料&#xff1a; 《动手学深度学习》 3.1 线性回归 3.1.1 线性回归的基本元素 样本&#xff1a; n n n 表示样本数&#xff0c; x ( i ) [ x 1 ( i ) , x 2 ( i ) , ⋯ , x d ( i ) ] x^{(i)}[x^{(i)}_1,x^{(i)}_2,\cdots,x^{(i)}_d] x(i)[x1(i)​,x2(i)​,⋯,xd(i)​…

特征选择算法 | Matlab实现基于ReliefF特征选择算法的分类数据特征选择 ReliefF

文章目录 效果一览文章概述部分源码参考资料效果一览 文章概述 特征选择算法 | Matlab实现基于ReliefF特征选择算法的分类数据特征选择 ReliefF 部分源码 %--------------------

写一个starter(spring boot)

前置知识 自动装配 自动装配的一个重要注解就是SpringBootApplication。它是一个复合注解&#xff0c;由四个元注解和另外三个注解组成。这三个注解是&#xff1a; ConfigurationEnableAutoConfigurationComponentScan Configuration Configuration 是 JavaConfig 形式的…

神经网络之VGG

目录 1.VGG的简单介绍 1.2结构图 3.参考代码 VGGNet-16 架构&#xff1a;完整指南 |卡格尔 (kaggle.com) 1.VGG的简单介绍 经典卷积神经网络的基本组成部分是下面的这个序列&#xff1a; 带填充以保持分辨率的卷积层&#xff1b; 非线性激活函数&#xff0c;如ReLU&a…

web安全php基础_php变量命名及其作用域

php变量命名规则 php变量命名规则 变量以 $ 符号开始&#xff0c;后面跟着变量的名称变量名必须以字母或者下划线字符开始变量名只能包含字母数字字符以及下划线&#xff08;A-z、0-9 和 _ &#xff09;变量名不能包含空格变量名是区分大小写的&#xff08;$y 和 $Y 是两个不…

SELECT * 会导致查询效率低的原因

SELECT * 会导致查询效率低的原因 前言一、适合SELECT * 的使用场景二、SELECT * 会导致查询效率低的原因2.1、数据库引擎的查询流程2.2、SELECT * 的实际执行过程2.3、使用 SELECT * 查询语句带来的不良影响 三、优化查询效率的方法四、总结 前言 因为 SELECT * 查询语句会查…

【如何成功加载 HuggingFace 数据集】不使用Colab,以ChnSentiCorp数据集为例

【如何成功加载 HuggingFace 数据集】不使用Colab&#xff0c;以ChnSentiCorp数据集为例 前置加载数据集尝试一&#xff1a;标准加载数据库代码尝试二&#xff1a;科学上网尝试三&#xff1a;把 Huggingface 的数据库下载到本地尝试3.5 创建 state.json彩蛋 前置 Huggingface …

MySQL用户管理

目录 用户管理 用户 用户信息 创建用户 删除用户 修改用户密码 数据库的权限 给用户授权 回收权限 用户管理 如果我们只能使用root用户&#xff0c;这样存在安全隐患。这时&#xff0c;就需要使用MySQL的用户管理。 用户 用户信息 MySQL中的用户&#xff0c;都存储…

手写操作系统--进入保护模式的开篇

之前我们讲的主引导扇区以及内核加载器等内容。都是在实模式下运行的。在实模式下寻址范围仅有1M&#xff0c;是远远不够我们用的。我们想要更大的内存空间&#xff0c;就得进入保护模式&#xff0c;实模式是一个历史遗留问题&#xff0c;本身是没有这个名字的。是因为有了保护…

Keil环境下CANopenNode移植到STM32问题记录(一)---printf重定向问题

文章目录 问题描述问题结决思考&#xff1a;相关文章 在直接将CANopenSTM32的示例工程直接移植到Keil环境下。 如果移植工程未实现printf函数重定向&#xff0c;则要注释掉log_printf下面的printf函数&#xff0c;使日志打印失效 /* Printf function of CanOpen app */ #define…

vue3的getCurrentInstance()方法拿到的实例对象中的proxy

getCurrentInstance方法拿到的是当前组件的实例对象 实例对象中的成员proxy是一个代理对象&#xff0c;可以通过访问代理对象来间接访问当前组件的实例对象 这样就不需要this&#xff0c;也可以操作当前组件的实例对象了 proxy对象就相当于当前组件的实例对象 proxy对象会对…