好像拖更了很久,很抱歉,最近想了一下css和js等内容还是不总结了,本来内容就多,不是一篇博客能说完的,而且我也只学了皮毛,以后还是通过实例的方式来分享一下学过的东西,希望能帮到大家。
目录
一、实现功能
二、实现方法
1.数据的传递
2.按钮的实现
3.全选按钮的实现
4.记录用户键盘数据
三、源代码(感兴趣自己试试)
总结
前言
最初了解到这个todolist的时候我还感觉挺简单的,但实现确实遇到了好多问题(我太菜了),而且在网上看大佬的文章,看不懂(哭),所以我会将实现思路和学到了一些新方法分享出来,希望能帮助理解,然后源代码粘到文末,也欢迎大家跟我一起交流。
一、实现功能
1.有一个输入框,记录想完成的事件,用户enter直接输入
2.有一个正在做任务框,记录正在做的任务
3.有一个已完成框,可以一键删除所有已完成任务
正在做的事项:
可以恢复到想完成,也可以进入删除框,
支持每个事项的点选,也支持一键转移
具体实现样式:
二、实现方法
1.数据的传递
筛选的思想(vue中也有filter组件)
computed: {
isNew () {
return this.list.filter(value => {
if (value.status === 'new') {
return value
}
})
},
isFinish () {
return this.list.filter(value => {
if (value.status === 'finish') {
return value
}
})
},
isDelete () {
return this.list.filter(value => {
if (value.status === 'delete') {
return value
}
})
}
},
利用了vue的计算属性,三个不同的变量分别代表创建框,正在做和已完成展示的属性
<el-checkbox v-for="item in isNew" :key="item.name" @change="turnFinish(item)" class="checkbox" style="margin-top:10px">{{item.name}}</el-checkbox>
页面搭建的时候使用v-for就可以了(我以前一直以为item in isNew只能是数组,其实方法也是可以的)
2.按钮的实现
删除按钮吧
不是其方法的实现,而是我在测试的时候发现,如果点击的过快,数据的传递会发生问题,因为你点击了,但请求接口的操作还没有执行完,这时候需要设置一个延时装置使用户不能点击那么快,el同样提供了loading组件https://element.eleme.cn/#/zh-CN/component/loading,我这里的实现思路就是 setTimeout(this.clickStatus, 100),给一个延时时间使用户不能点击。
HTML代码
<el-button type="text" style="width:30px; color:#E6A23C" @click="turnDelete(item)" :disabled="canClick">删除</el-button>
:disabled属性上绑定一个变量,默认为false,当执行事件的时候变为true,这时候用户就不能点击,然后等计时结束再变成false,this.clickStatus实现的就是改变这个值。
turnDelete (item) {
if (this.canClick === false) {
this.canClick = true
item.status = 'delete'
console.log(this.list)
setTimeout(this.clickStatus, 100)
}
},
clickStatus () {
this.canClick = false
},
3.全选按钮的实现
需求中提到了一键转移要求,就是点击全选时候可将旗下所有数据状态改变,全选功能的实现el也给出了案例https://element.eleme.cn/#/zh-CN/component/checkbox
checked和indeterminate,具体说明如下: 一个控制样式一个控制是否点选
感兴趣可以自行研究,我这里提供结果以便大家理解:
全选:checked = true ,indeterminate = false
全不选:checked = false,indeterminate = false
选了几个:checked = false,indeterminate = true
所以实现自己的按钮的时候要严格按照他提供的逻辑去写
// 全选按钮绑定checkAll事件
<el-checkbox v-model="checkAll" :indeterminate="isIndeterminate" @change="handleCheckAllChange" style="width:60%; zoom:160%">click all</el-checkbox>
// 下面展示的check-group要绑定handleCheckedCitiesChange,这样才是双向实现
<el-checkbox-group v-model="alreadyChecked" @change="handleCheckedCitiesChange">
<el-checkbox v-for="item in isFinish" :key="item.name" :label="item.name" class="checkbox">
{{item.name}}
<el-button type="text" style="width:30px" @click="turnNew(item)" :disabled="canClick">恢复</el-button>
<el-button type="text" style="width:30px; color:#E6A23C" @click="turnDelete(item)" :disabled="canClick">删除</el-button>
</el-checkbox>
具体实现逻辑仿照提供案例写,因为doing框的数据并不就是list的全部数据,而是status = ‘finish’这一类数据,所以判断前要先进行数据的筛选(我写的时候还犯过特别低级的错误,函数内部定义的变量,在调用的时候使用this. variable,然后出来就是undefine)
遍历一个数组内部数据map和forEach都可以,我还没有比较过这两种方法的区别,下次研究一下
handleCheckAllChange (val) {
this.alreadyChecked = val ? this.list.map(x => {
if (x.status === 'finish') {
return x.name
}
}) : []
this.isIndeterminate = false
},
handleCheckedCitiesChange (value) {
let checkedCount = value.length
let finishCount = 0
this.list.forEach(element => {
if (element.status === 'finish') {
finishCount = finishCount + 1
}
})
this.checkAll = checkedCount === finishCount
this.isIndeterminate = checkedCount > 0 && checkedCount < finishCount
}
4.记录用户键盘数据
如何在用户使用enter的时候就记录下相关数据?
可以使用keyup属性,这是jQuery相关知识,我还没有学过,感兴趣自行了解。
@keyup.enter.native="enter"
三、源代码(感兴趣自己试试)
HTML
<template>
<div>
<el-row>
<el-col :span="24">
<div class="bg-purple-dark grid-content">
<el-tooltip effect="dark" content="记录每日代办" placement="right">
<p class="header">Todolist</p>
</el-tooltip>
</div>
</el-col>
</el-row>
<el-row>
<el-col :span="8">
<div class="bg-purple grid-content">
<el-tooltip effect="dark" content="记录想做的事情" placement="top">
<h3 class="subtitle">Wating</h3>
</el-tooltip>
<el-input placeholder="please write down something" v-model="input" clearable @keyup.enter.native="enter"></el-input>
<el-checkbox v-for="item in isNew" :key="item.name" @change="turnFinish(item)" class="checkbox" style="margin-top:10px">{{item.name}}</el-checkbox>
</div>
</el-col>
<el-col :span="8">
<div class="bg-purple-light grid-content">
<el-tooltip effect="dark" content="正在做的事项" placement="top">
<h3 class="subtitle">Doing</h3> </el-tooltip>
<div>
<el-checkbox v-model="checkAll" :indeterminate="isIndeterminate" @change="handleCheckAllChange" style="width:60%; zoom:160%">click all</el-checkbox>
<el-tooltip effect="light" content="一键恢复" placement="left">
<el-button type="info" icon="el-icon-refresh-left" circle @click="allTurnNew"></el-button>
</el-tooltip>
<el-tooltip effect="light" content="一键删除" placement="right">
<el-button type="warning" icon="el-icon-delete" circle @click="allTurnDelete"></el-button>
</el-tooltip>
</div>
<el-checkbox-group v-model="alreadyChecked" @change="handleCheckedCitiesChange">
<el-checkbox v-for="item in isFinish" :key="item.name" :label="item.name" class="checkbox">
{{item.name}}
<el-button type="text" style="width:30px" @click="turnNew(item)" :disabled="canClick">恢复</el-button>
<el-button type="text" style="width:30px; color:#E6A23C" @click="turnDelete(item)" :disabled="canClick">删除</el-button>
</el-checkbox>
</el-checkbox-group>
</div>
</el-col>
<el-col :span="8">
<div class="bg-purple grid-content">
<el-tooltip effect="dark" content="已经完成的事项" placement="top">
<h3 class="subtitle">Finish</h3> </el-tooltip>
<el-tooltip effect="light" content="清空内容" placement="right">
<el-button type="danger" round @click="clean">清空回收站</el-button>
</el-tooltip>
<p v-for="item in isDelete" :key="item.name" class="delete">{{item.name}}</p>
</div>
</el-col>
</el-row>
</div>
</template>
JS
<script>
export default {
data () {
return {
input: '',
list: [],
// for clickAll checkbox
checkAll: false,
isIndeterminate: false,
finishList: [],
alreadyChecked: [],
canClick: false
}
},
computed: {
isNew () {
return this.list.filter(value => {
if (value.status === 'new') {
return value
}
})
},
isFinish () {
return this.list.filter(value => {
if (value.status === 'finish') {
return value
}
})
},
isDelete () {
return this.list.filter(value => {
if (value.status === 'delete') {
return value
}
})
}
},
methods: {
// record the things people input
enter () {
let isRepeat = false
this.list.map(x => {
if (x.name === this.input) {
isRepeat = true
}
})
if (this.input === '') {
this.$message({
message: 'please input something',
type: 'warning'
})
} else if (isRepeat === true) {
this.$message('this list is repeat, please write another')
} else {
this.list.push({
name: this.input,
status: 'new'
})
}
this.input = ''
console.log(this.list)
},
turnFinish (item) {
item.status = 'finish'
},
turnNew (item) {
if (this.canClick === false) {
this.canClick = true
item.status = 'new'
setTimeout(this.clickStatus, 100)
}
},
turnDelete (item) {
if (this.canClick === false) {
this.canClick = true
item.status = 'delete'
console.log(this.list)
setTimeout(this.clickStatus, 100)
}
},
clean () {
this.list.forEach(element => {
if (element.status === 'delete') {
element.status = 'done'
}
})
},
clickStatus () {
this.canClick = false
},
allTurnNew () {
if (this.checkAll === true && this.isIndeterminate === false) {
this.list.forEach(element => {
if (element.status === 'finish') {
element.status = 'new'
}
})
this.checkAll = false
// 取消对于所有事项的勾选
this.alreadyChecked = []
}
},
allTurnDelete () {
if (this.checkAll === true && this.isIndeterminate === false) {
this.list.forEach(element => {
if (element.status === 'finish') {
element.status = 'delete'
}
})
this.checkAll = false
}
},
handleCheckAllChange (val) {
this.alreadyChecked = val ? this.list.map(x => {
if (x.status === 'finish') {
return x.name
}
}) : []
this.isIndeterminate = false
},
handleCheckedCitiesChange (value) {
let checkedCount = value.length
let finishCount = 0
this.list.forEach(element => {
if (element.status === 'finish') {
finishCount = finishCount + 1
}
})
this.checkAll = checkedCount === finishCount
this.isIndeterminate = checkedCount > 0 && checkedCount < finishCount
}
}
}
</script>
总结
如果觉得对你有帮助,请点一个赞吧,你的支持是作者最大的动力!