var data = (localStorage.getItem('todolist'))?
JSON.parse(localStorage.getItem('todolist')) : {
todo: [],
done : [] // 键值对 用冒号
}; renderTodoList(); var oBtnAdd = document.getElementById('add');
var oInput = document.getElementById('input'); // var oLi = document.createElement('li');
// 这个li必须在function里面获取,否则li每次都是直接覆盖,没有create新的li。 // 问题: 输入框复制了很多字之后, 闪烁光标不见了? oBtnAdd.addEventListener('click', newTodo); oInput.addEventListener('keydown', function(e){
if( e.code === 'Enter' || e.code === 'NumpadEnter') newTodo();
}); function newTodo(){
var value = oInput.value; if(oInput.value) {
addItemToDOM(value);
data.todo.push(value);
dataUpdate();
}
oInput.value = '';
}; function renderTodoList() {
if (!data.todo.length && !data.done.length) return;
  

// 如果 data数据里的两个数组都为空, 即没有初始数据需要渲染, 就返回。
 
// !!! 记住这里的! 感叹号用法,表示数组为空。
// 如果数组长度为 0 => false ( 0 的布尔值是false )
// !0 => true
// 也就是两个都满足true,就返回。
// 即两个都为空时,不运行后面的函数。
for (var i = 0; i < data.todo.length; i++) {
var value = data.todo[i];
addItemToDOM(value);
}
for (var j = 0; j < data.done.length; j++) {
var value = data.done[j];
addItemToDOM(value, true);
}
}; // 点击完成的按钮, 切换事项完成的情况。
function completed(){
var itemLi = this.parentNode.parentNode; //保存旧的数据 var parentUl = itemLi.parentNode;
var id = parentUl.id;
var value = itemLi.innerText; if (id === 'todoID') {
data.todo.splice(data.todo.indexOf(value), 1);
data.done.push(value);
} else{
data.done.splice(data.todo.indexOf(value), 1);
data.todo.push(value);
}; // 如果这个li是完成的,就变成未完成,反之就是完成。 //(id === 'todo')? id = 'completed': id = 'todo';
// 直接改变Ul的id值是错的, 这样并没改变li元素所在的环境, 只是给父Ul赋值新的ID名而已。 // 判断Ul的ID 是不是todo, 即判断, 要移动的li元素 在todo列表里,还是在done列表里。
// 然后把li元素放到和初始Ul的ID 相反的Ul里面去。 即 移动这条清单到和之前相反的列表里。 // 获取页面中已经存在的Ul, 并把和初始Ul相反的Ul 确定为移动的目标,存为target
var target = (id === 'todoID') ? document.getElementById('doneID'):document.getElementById('todoID'); parentUl.removeChild(itemLi);
// 这里删掉的还是原本的Ul里的li,旧的父子关系。 都是前面存下来的。 target.insertBefore(itemLi, target.children[0]);
// 插入li元素, 插到新获取的target里。 // 旧数据赋值给新的li
// 删掉旧的li dataUpdate();
}; function removeBtn(){
var deleteLi = this.parentNode.parentNode;
var parent = deleteLi.parentNode; var id = parent.id;
var value = deleteLi.innerText;
//点击按钮,要删掉的是该行li的文字内容。即innerText if (id === 'todoID') {
data.todo.splice(data.todo.indexOf(value), 1);
} else{
data.done.splice(data.done.indexOf(value), 1);
} dataUpdate();
parent.removeChild(deleteLi);
}; function addItemToDOM(text, done){ var removeSVG = '<svg version="1.1" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" viewBox="0 0 22 22" style="enable-background:new 0 0 22 22;" xml:space="preserve"> <g> <g> <path class="fill" d="M16.1,3.6h-1.9V3.3c0-1.3-1-2.3-2.3-2.3h-1.7C8.9,1,7.8,2,7.8,3.3v0.2H5.9c-1.3,0-2.3,1-2.3,2.3v1.3 c0,0.5,0.4,0.9,0.9,1v10.5c0,1.3,1,2.3,2.3,2.3h8.5c1.3,0,2.3-1,2.3-2.3V8.2c0.5-0.1,0.9-0.5,0.9-1V5.9 C18.4,4.6,17.4,3.6,16.1,3.6z M9.1,3.3c0-0.6,0.5-1.1,1.1-1.1h1.7c0.6,0,1.1,0.5,1.1,1.1v0.2H9.1V3.3z M16.3,18.7 c0,0.6-0.5,1.1-1.1,1.1H6.7c-0.6,0-1.1-0.5-1.1-1.1V8.2h10.6L16.3,18.7L16.3,18.7z M17.2,7H4.8V5.9c0-0.6,0.5-1.1,1.1-1.1h10.2 c0.6,0,1.1,0.5,1.1,1.1V7z"/> </g> <g> <g> <path class="fill" d="M11,18c-0.4,0-0.6-0.3-0.6-0.6v-6.8c0-0.4,0.3-0.6,0.6-0.6s0.6,0.3,0.6,0.6v6.8C11.6,17.7,11.4,18,11,18z"/> </g> <g> <path class="fill" d="M8,18c-0.4,0-0.6-0.3-0.6-0.6v-6.8C7.4,10.2,7.7,10,8,10c0.4,0,0.6,0.3,0.6,0.6v6.8C8.7,17.7,8.4,18,8,18z" /> </g> <g> <path class="fill" d="M14,18c-0.4,0-0.6-0.3-0.6-0.6v-6.8c0-0.4,0.3-0.6,0.6-0.6c0.4,0,0.6,0.3,0.6,0.6v6.8 C14.6,17.7,14.3,18,14,18z"/> </g> </g> </g> </svg>';
var completeSVG = '<svg version="1.1" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" viewBox="0 0 22 22" style="enable-background:new 0 0 22 22;" xml:space="preserve"> <g> <path class="fill" d="M9.7,14.4L9.7,14.4c-0.2,0-0.4-0.1-0.5-0.2l-2.7-2.7c-0.3-0.3-0.3-0.8,0-1.1s0.8-0.3,1.1,0l2.1,2.1l4.8-4.8 c0.3-0.3,0.8-0.3,1.1,0s0.3,0.8,0,1.1l-5.3,5.3C10.1,14.3,9.9,14.4,9.7,14.4z"/> </g> </svg>'; var Buttons = document.createElement('div');
Buttons.classList.add('buttons'); var oDel = document.createElement('button');
oDel.classList.add('delete');
oDel.innerHTML = removeSVG;
oDel.addEventListener('click', removeBtn); var oDone = document.createElement('button');
oDone.classList.add('done');
oDone.innerHTML = completeSVG;
oDone.addEventListener('click', completed); Buttons.appendChild(oDel);
Buttons.appendChild(oDone); var oLi = document.createElement('li');
oLi.innerText = text;
oLi.appendChild(Buttons); var oUl = (done) ? document.getElementById('doneID'):document.getElementById('todoID'); // if(oUl.children[0]){
// oUl.insertBefore(oLi, oUl.children[0]);
// }else{
// oUl.appendChild(oLi);
// };
oUl.insertBefore(oLi, oUl.children[0]);
// 为什么这个children不需要判断第0位是否有值? dataUpdate();
};
// 创建div,两个按钮,填充svg
/*function btnSvg(){
var oDiv = document.createElement('div');
var oDel = document.createElement('button');
var oDone = document.createElement('button');
var removeSVG = '<svg version="1.1" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" viewBox="0 0 22 22" style="enable-background:new 0 0 22 22;" xml:space="preserve"> <g> <g> <path class="fill" d="M16.1,3.6h-1.9V3.3c0-1.3-1-2.3-2.3-2.3h-1.7C8.9,1,7.8,2,7.8,3.3v0.2H5.9c-1.3,0-2.3,1-2.3,2.3v1.3 c0,0.5,0.4,0.9,0.9,1v10.5c0,1.3,1,2.3,2.3,2.3h8.5c1.3,0,2.3-1,2.3-2.3V8.2c0.5-0.1,0.9-0.5,0.9-1V5.9 C18.4,4.6,17.4,3.6,16.1,3.6z M9.1,3.3c0-0.6,0.5-1.1,1.1-1.1h1.7c0.6,0,1.1,0.5,1.1,1.1v0.2H9.1V3.3z M16.3,18.7 c0,0.6-0.5,1.1-1.1,1.1H6.7c-0.6,0-1.1-0.5-1.1-1.1V8.2h10.6L16.3,18.7L16.3,18.7z M17.2,7H4.8V5.9c0-0.6,0.5-1.1,1.1-1.1h10.2 c0.6,0,1.1,0.5,1.1,1.1V7z"/> </g> <g> <g> <path class="fill" d="M11,18c-0.4,0-0.6-0.3-0.6-0.6v-6.8c0-0.4,0.3-0.6,0.6-0.6s0.6,0.3,0.6,0.6v6.8C11.6,17.7,11.4,18,11,18z"/> </g> <g> <path class="fill" d="M8,18c-0.4,0-0.6-0.3-0.6-0.6v-6.8C7.4,10.2,7.7,10,8,10c0.4,0,0.6,0.3,0.6,0.6v6.8C8.7,17.7,8.4,18,8,18z" /> </g> <g> <path class="fill" d="M14,18c-0.4,0-0.6-0.3-0.6-0.6v-6.8c0-0.4,0.3-0.6,0.6-0.6c0.4,0,0.6,0.3,0.6,0.6v6.8 C14.6,17.7,14.3,18,14,18z"/> </g> </g> </g> </svg>';
var completeSVG = '<svg version="1.1" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" viewBox="0 0 22 22" style="enable-background:new 0 0 22 22;" xml:space="preserve"> <g> <path class="fill" d="M9.7,14.4L9.7,14.4c-0.2,0-0.4-0.1-0.5-0.2l-2.7-2.7c-0.3-0.3-0.3-0.8,0-1.1s0.8-0.3,1.1,0l2.1,2.1l4.8-4.8 c0.3-0.3,0.8-0.3,1.1,0s0.3,0.8,0,1.1l-5.3,5.3C10.1,14.3,9.9,14.4,9.7,14.4z"/> </g> </svg>'; oDiv.classList.add('buttons');
oDel.classList.add('delete');
oDone.classList.add('done'); oDel.innerHTML = removeSVG; // 点击删除事件写在创建元素的时候,对应的就是每个按钮自己的事件。 不需要for循环。
oDel.addEventListener('click', removeBtn);
// 从onclick 改成 addEventListener 就可以把外部函数包含this的调用了。
// !!! 需要搞清楚这个原理。 oDone.innerHTML = completeSVG; oDone.addEventListener('click', completed);
//括号里不能直接放 completed(), 这里是调用函数, 不是调用函数处理的结果。 oDiv.appendChild(oDel);
oDiv.appendChild(oDone); return oDiv;
}*/ function dataUpdate(){
localStorage.setItem('todolist', JSON.stringify(data));
// stringify方法里的data从哪来?? --在前面数组操作里已经操作过了
};

JS错误记录 - To-do List的更多相关文章

  1. JS错误记录 - 微博发布

    <style> *{ margin: 0; padding: 0;} #ul1{ width: 400px; height: 400px; border: 1px solid #000; ...

  2. JS错误记录 - 右侧悬浮框 - 缓冲运动

    本次练习错误总结: 1.  正确: startMove( document.documentElement.clientHeight - oDiv.offsetHeight + scrollTop); ...

  3. JS错误记录 - dom操作 - 排序

    本次练习错误总结: 1. for循环要套到按钮的onclick里面,否则onclick点击事件无法依次执行. 2. var n1, var n2 这两个变量是arr.sort排序使用的,所以应该放在s ...

  4. JS错误记录 - 事件 - 拖拽

    错误总结: 1. var disX = 0;   现在window.onload里声明变量,而不是在事件oDiv.onmousedown里面声明并赋值. 对于这个还不是很明白. 2. onmoused ...

  5. JS错误记录 - 按左右箭头div移动、一串div跟着鼠标移动

    本次练习错误总结: 1. div跟着用户操作而移动,首先必须要绝对定位,否则无法移动. 2. if条件语句里面是双等号,不是单等号(赋值). 3. 坐标值没有Right,只能offsetLeft 加减 ...

  6. JS错误记录 - getStyle代替offset、任意值运动框

    本次练习错误总结: 1. 改变border的宽度,属性名称不是直接写border,而是borderWidth. 2. 运动函数 -- 清除定时器 -- 开启新的定时器.  不是在新定时器开启之后再清除 ...

  7. JS错误记录 - fgm练习 - 函数传参

    <script> window.onload = function() { var oBtn = document.getElementsByTagName('button')[0]; v ...

  8. JS错误记录 - 记录上次登陆的用户名

    <script> //步骤 1.submit => 用户名存进cookie 2. onload => 从cookie读取用户名 window.onload = function ...

  9. JS错误记录 - 取消事件冒泡、按钮、回车、ctrl回车提交留言

    window.onload = function () { var oDiv = document.getElementById('div1'); var oBtn = document.getEle ...

随机推荐

  1. 深入理解Struts2

    简单介绍 Struts 2是Struts的下一代产品.是在 struts 1和WebWork的技术基础上进行了合并的全新的Struts 2框架. 其全新的Struts 2的体系结构与Struts 1的 ...

  2. Android禁止ViewPager的左右滑动

    转载请注明出处:http://blog.csdn.net/allen315410/article/details/40744287 有时候在开发中会遇到一些"诡异"的要求,比方在V ...

  3. Python数据可视化——散点图

    PS: 翻了翻草稿箱. 发现竟然存了一篇去年2月的文章...尽管naive.还是发出来吧... 本文记录了python中的数据可视化--散点图scatter, 令x作为数据(50个点,每一个30维), ...

  4. FSM之三--代码风格

    FSM设计之一http://www.cnblogs.com/qiweiwang/archive/2010/11/28/1890244.html Moore型状态机与mealy型状态机相比,由于其状态输 ...

  5. POJ 3265 DP

    思路: f[i][j]表示前i天能做j道题 (是做 不是做完) if(f[i-1][k]) if(suma[j]-suma[k]+g[i-1][k]<=n) f[i][j]=1,g[i][j]= ...

  6. java带package的编译

    ProcessBuilder pb = new ProcessBuilder("cmd", "/c", "java -cp d:\\TEST com/ ...

  7. 传说用户发来的请求是在JIoEndpoint的accept函数中接收的,是tomact与外界交互的分界点

    传说用户发来的请求是在JIoEndpoint的accept函数中接收的, 这是tomact与外界交互的分界点,所以来研究一下, >>>>>>>>> ...

  8. CrawlSpider爬取读书网

    crawlspider用于定义一些规则用于提取页面符合规则的数据,然后继续爬取. 一.开始一个读书网项目 scrapy startproject 项目名称cd 项目名称/项目名称/spidersscr ...

  9. .js控制一次加载一张图片,加载完后再加载下一张

    js怎么控制一次加载一张图片,加载完后再加载下一张 (1)方法1 (1)方法2

  10. ArcGIS Engine中添加点、线、面元素

    转自原文 ArcGIS Engine中添加点.线.面元素 此种方式为IElement的方式在axMapControl的GraphicsContainer中好绘制图形. //画点 IPoint pt = ...