第15天的内容是类似一个todolist
把内容存到localStorage里防止每次打开就没有之前的内容
js脚本内嵌在html里,css写在另一个文件里
HTML
写了一个logo放在上面
下面一个div里放着列表、输入框和提交按钮
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>LocalStorage</title>
<link rel="stylesheet" href="style.css">
</head>
<body>
<!-- 用了张本地照片作为logo -->
<img src="/15 - LocalStorage/logo.jpg" alt="" class="logo">
<div class="wrapper">
<h2>To Do It</h2>
<p></p>
<ul class="plates">
<li>Loading...</li>
</ul>
<form class="add-items">
<input type="text" name="item" placeholder="Item Name" required>
<input type="submit" value=" -Add Item- ">
</form>
<p class="clear">clear all</p>
</div>
</body>
</html>
这个不是重点
JavaScript
如果不考虑list内容需不需要checked,只需要一个列表的话
只要addItem和populateList函数就够了,然后加个监听
toggleDone是为了刷新是否checked,还加了个clear的监听
<script>
//选取页面内容
const addItems = document.querySelector('.add-items');
const itemsList = document.querySelector('.plates');
const clear_ = document.querySelector('.clear');
//从缓存拿数组数据或新建数组
var items = JSON.parse(localStorage.getItem('items')) ||[];
//addItem函数用于将输入框内容添加到数组里
function addItem(e){
//这个preventDefault()是为了防止自动刷新
e.preventDefault();
const text = this.querySelector('[name=item]').value;
const item = {text:text , checked :false};
items.push(item);
this.reset();
populateList(items,itemsList);
localStorage.setItem('items',JSON.stringify(items));
}
//populateList用于添加内容到html里
function populateList(plates = [],plateslist){
plateslist.innerHTML = plates.map((plate,i) =>{
return `
<li>
<input type = 'checkbox' data-index=${i} id = "item${i}" ${plate.checked ? 'checked' : ''} >
<label for="item${i}"> ${plate.text} </label>
</li>
`;
}).join('');
}
//toggleDone是用于刷新缓存里的item是否完成选项
function toggleDone(e){
if (!e.target.matches('input')) return;
items[e.target.dataset.index].checked = !items[e.target.dataset.index].checked;
localStorage.setItem('items', JSON.stringify(items));
}
//添加监听
addItems.addEventListener('submit',addItem);
itemsList.addEventListener('click',toggleDone);
clear_.addEventListener('click',()=>{
items = [];
populateList(items, itemsList);
localStorage.setItem('items', JSON.stringify(items));
});
//第一次运行刷新items
populateList(items,itemsList);
</script>
用到的函数
- Array.map() 返回一个新数组
- Array.push() 将内容添加到数组里
- JSON 一个数据储存与读取库,可以按一定的规则存储数据
- JSON.Stringfy() 将数组转化为JSON格式String
- JSON.parse() 还原JSON字符串为数组或字典
- preventDefault() 阻止自带函数
讨论
实现目标效果不是很难,或者说比我想象的简单一点,但用localStorage总觉得有点问题。
如果是服务端的话,那应该会在服务器哪里存着,然后根据http请求的头文件找对应文件。
css部分觉得难搞多了,给input按钮加了个:hover和:actice,果然使用体验好多了,没有反馈的交互按键真是不合理的东西。
CSS源码
html {
box-sizing: border-box;
background:url('/15\ -\ LocalStorage/photo-1551300444-2a7ea9b69f2e.jpg') center no-repeat;
background-size:cover;
/* min-height:100vh;*/
display:flex;
justify-content: center;
/* align-items: center; */
text-align: center;
font-family: Futura,"Trebuchet MS",Arial,sans-serif
}
*, *:before, *:after {box-sizing: inherit; }
img {
fill:white;
background: rgba(255,255,255,0.4);
padding: 20px;
border-radius: 50%;
width:150px;
margin-bottom: 20px;
}
.wrapper {
padding: 20px;
max-width: 350px;
background: rgba(255,255,255,0.95);
box-shadow: 0 0 0 10px rgba(0,0,0,0.1);
padding-bottom: 5px;
}
h2 {
text-align: center;
margin: 0;
font-weight: 200;
}
.plates {
margin: 0;
padding: 0;
text-align: left;
list-style: none;
}
.plates li {
border-bottom: 1px solid rgba(0,0,0,0.2);
padding: 10px 0;
font-weight: 100;
display: flex;
}
.plates label {
flex:1;
cursor: pointer;
}
.plates input {
display: none;
}
.plates input + label:before {
content: '⬜️';
margin-right: 10px;
}
.plates input:checked + label:before {
content: '☑️';
}
.add-items {
margin-top: 20px;
}
.add-items input {
padding:8px;
padding-left: 12px;
padding-right: 12px;
outline:0;
border:1px solid rgba(0,0,0,0.1);
margin-left: 10px;
border-radius: 20px;
cursor: pointer;
box-shadow: 2px 2px 1px rgba(0,0,0,0.1);
text-shadow: 1px 1px 2px rgba(0,0,0,.2);
}
.add-items input:hover{
background-color: #81ecec;
}
.add-items input:active{
background-color: #0984e3;
}
.add-items input[type=text] {
border-radius: 12px;
cursor: text;
}
.add-items input[type=text]:hover {
background-color: #fff;
}
.clear{
margin-top: 10px;
margin-bottom: 10px;
width: 60px;
color: #b2bec3;
margin-left: auto;
margin-right: auto;
}
.clear:hover{
cursor: pointer;
}
.clear:active{
color: #0984e3;
}
body{
margin-top: 100px;
}